Windows 可移动媒体事件 ID 4656 未报告所有信息

问题描述 投票:0回答:1

我正在使用 PowerShell 生成可移动媒体报告。我拥有所有高级审核设置,除了我无法弄清楚的一项之外,它按预期工作。

我插入了拇指驱动器,然后创建了一个新文件夹。当我收集 4656(和 4663)事件时,会为“新文件夹”生成一个 4656 事件,但是,对象名称不包含实际创建的文件夹的名称,它只是指出“新文件夹”。我正在寻找创建的实际文件夹。以下是创建对象的事件中返回的示例:

    Object Name:        \Device\HarddiskVolume3\Temp\New folder

没有生成包含实际文件夹名称(我可以找到)的事件,它们只是简单地指出“新文件夹”。我需要将其与其他事件关联起来吗?我已将返回的事件转换为 XML,但仍然无法在任何地方找到实际的文件夹名称。预先感谢您提供的任何帮助。

windows powershell security audit event-viewer
1个回答
0
投票

我不知道有任何设置可以使事件日志服务在日志条目中呈现卷标,但您可以通过解析与分区

X
关联的卷标来转换对象路径,其中
X
是数字以下
\Device\HarddiskVolume

注意:下面的示例代码使用 PowerShell 6.1 中引入的

-replace '...', {...}
语法 - 对于 PowerShell 5.1 及更早版本,请参阅本答案底部的替代语法

$objectNameData = $eventXml.SelectSingleNode('//Event/EventData/Data[@Name="ObjectName"]')

# yields "\Device\HarddiskVolume3\Temp\New Folder"
$objectNameData.InnerText 

# yields "C:\Temp\New Folder"
$objectNameData.InnerText -replace '^\\Device\\HarddiskVolume(\d+)\\',{
    (Get-Partition -PartitionNumber $_.Groups[1].Value).AccessPaths.Where({$_ -like '?:\*'}, 'First')[0]
}

为了避免一遍又一遍地重复查询同一分区的 WMI,请使用哈希表来缓存已解析的路径:

$volumeLabelCache = @{}

foreach ($eventXml in $events) {
  $objectPath = $eventXml.SelectSingleNode('//Event/EventData/Data[@Name="ObjectName"]').InnerText 
  $resolvedPath = $objectPath -replace '^\\Device\\HarddiskVolume(\d+)\\',{
    $partitionID = $_.Groups[1].Value
    if (-not $volumeLabelCache.Contains($partitionID)) {
      # cache volume label so we don't need to query the same partition id again
      $volumeLabelCache[$partitionID] = (Get-Partition -PartitionNumber $partitionID).AccessPaths.Where({$_ -like '?:\*'}, 'First')[0]
      if (-not $volumeLabelCache[$partitionID]){
        # looks like we failed to resolve mount point from partition id, return original path
        return $_.Value
      }
    }

    # ... otherwise replace partition part of the object path with volume label 
    return $volumeLabelCache[$partitionID]
  }

  Write-Host "Resolved path '$resolvedPath' from '$objectPath'"
}

对于 6.1 之前的 PowerShell 版本,您可以直接调用

[regex]::Replace
来访问内联回调:

'input' -replace 'pattern', { substitution code <# over $_ #> }
# becomes
[regex]::Replace('input', 'pattern', {param($m) substitution code <# over $m #> })

使用上面的示例代码,将是这样的:

  [regex]::Replace($objectPath, '^\\Device\\HarddiskVolume(\d+)\\', {
    param($m)
    $partitionID = $m.Groups[1].Value
    if (-not $volumeLabelCache.Contains($partitionID)) {
      # cache volume label so we don't need to query the same partition id again
      $volumeLabelCache[$partitionID] = (Get-Partition -PartitionNumber $partitionID).AccessPaths.Where({$_ -like '?:\*'}, 'First')[0]
      if (-not $volumeLabelCache[$partitionID]){
        # looks like we failed to resolve mount point from partition id, return original path
        return $m.Value
      }
    }

    # ... otherwise replace partition part of the object path with volume label 
    return $volumeLabelCache[$partitionID]
  }
最新问题
© www.soinside.com 2019 - 2025. All rights reserved.