[Console]::OutputEncoding = [Text.Encoding]::UTF8 $ErrorActionPreference = "Stop" function H2B($hex) { if (-not $hex) { return $null } $n = $hex.Length / 2 $b = New-Object byte[] $n for ($i = 0; $i -lt $n; $i++) { $b[$i] = [Convert]::ToByte($hex.Substring(2*$i, 2), 16) } return $b } $lines = [IO.File]::ReadAllLines("$env:TEMP\opencode\ss123.tsv") $acks = New-Object System.Collections.ArrayList $qs = New-Object System.Collections.ArrayList foreach ($l in $lines) { $p = $l -split "`t"; if ($p.Count -lt 5 -or -not $p[4]) { continue } $b = H2B $p[4]; if ($b.Length -lt 0x2A) { continue } $t = [double]$p[0] if ($p[1] -eq "192.168.123.1" -and $p[2] -eq "192.168.123.113" -and $b.Length -eq 42 -and [int]$b[4] -eq 4) { $v = [int]$b[0x20] + [int]$b[0x21]*256 + [int]$b[0x22]*65536 + [int]$b[0x23]*16777216 [void]$acks.Add(@{ t=$t; v=$v; hex=(($b[0x1A..0x29] | ForEach-Object { $_.ToString("x2") }) -join "") }) } if ($p[1] -eq "192.168.123.113" -and $p[2] -eq "192.168.123.1" -and $b.Length -gt 0x52 -and $b.Length -lt 2000 -and [int]$b[4] -eq 4 -and $b[0x20] -eq 2 -and $b[0x21] -eq 0 -and $b[0x30] -eq 0 -and $b[0x3C] -eq 1) { [void]$qs.Add(@{ t=$t; cmd=$b[0x3D] }) } } Write-Host ("42B 帧数={0}" -f $acks.Count) # 0x20-0x23 值序列: 单调性 + 间隔 $mono = 0; $notMono = 0; $gaps = @{} for ($i = 1; $i -lt $acks.Count; $i++) { $d = $acks[$i].v - $acks[$i-1].v if ($d -gt 0) { $mono++ } else { $notMono++ } $gk = "$d" if (-not $gaps.ContainsKey($gk)) { $gaps[$gk] = 0 }; $gaps[$gk]++ } Write-Host ("0x20-0x23 值: 递增={0} 非递增={1}" -f $mono, $notMono) Write-Host "--- 相邻差值分布 ---" $gaps.GetEnumerator() | Sort-Object { [int]$_.Key } | Select-Object -First 10 | ForEach-Object { Write-Host (" 差={0} : {1}" -f $_.Key, $_.Value) } Write-Host "--- 前 8 个 42B 帧 (时间/值/hex) ---" foreach ($a in ($acks | Select-Object -First 8)) { Write-Host (" t={0,8:F3} v={1} hex={2}" -f $a.t, $a.v, $a.hex) } Write-Host "--- 后 4 个 ---" foreach ($a in ($acks | Select-Object -Last 4)) { Write-Host (" t={0,8:F3} v={1} hex={2}" -f $a.t, $a.v, $a.hex) } # 42B 帧与 cmd 查询的时间相关性: 每个 42B 前 50ms 内最近的查询 cmd $byCmd = @{} foreach ($a in $acks) { $best = $null for ($i = $qs.Count - 1; $i -ge 0; $i--) { if ($qs[$i].t -le $a.t) { $best = $qs[$i]; break } } $k = if ($best -and (($a.t - $best.t) -lt 0.05)) { "cmd={0:x2}" -f $best.cmd } else { "无临近查询" } if (-not $byCmd.ContainsKey($k)) { $byCmd[$k] = 0 }; $byCmd[$k]++ } Write-Host "--- 42B 帧前 50ms 内最近查询 ---" $byCmd.GetEnumerator() | Sort-Object { [int]$_.Value } -Descending | ForEach-Object { Write-Host (" {0} : {1}" -f $_.Key, $_.Value) } # 42B 帧间时间隔 $tlast = $null; $tg = New-Object System.Collections.ArrayList foreach ($a in $acks) { if ($null -ne $tlast) { [void]$tg.Add([int](($a.t - $tlast) * 1000)) }; $tlast = $a.t } $tgs = $tg | Sort-Object Write-Host ("--- 42B 帧时间隔ms: min={0} 中位={1} max={2}" -f $tgs[0], $tgs[[int]($tgs.Count/2)], $tgs[-1])