|
|
|
@ -12,7 +12,7 @@
|
|
|
|
|
#
|
|
|
|
|
# Stephane Lesimple
|
|
|
|
|
#
|
|
|
|
|
VERSION='0.45'
|
|
|
|
|
VERSION='0.46'
|
|
|
|
|
|
|
|
|
|
trap 'exit_cleanup' EXIT
|
|
|
|
|
trap '_warn "interrupted, cleaning up..."; exit_cleanup; exit 1' INT
|
|
|
|
@ -25,6 +25,7 @@ exit_cleanup()
|
|
|
|
|
[ -n "${kerneltmp2:-}" ] && [ -f "$kerneltmp2" ] && rm -f "$kerneltmp2"
|
|
|
|
|
[ -n "${mcedb_tmp:-}" ] && [ -f "$mcedb_tmp" ] && rm -f "$mcedb_tmp"
|
|
|
|
|
[ -n "${intel_tmp:-}" ] && [ -d "$intel_tmp" ] && rm -rf "$intel_tmp"
|
|
|
|
|
[ -n "${linuxfw_tmp:-}" ] && [ -f "$linuxfw_tmp" ] && rm -f "$linuxfw_tmp"
|
|
|
|
|
[ "${mounted_debugfs:-}" = 1 ] && umount /sys/kernel/debug 2>/dev/null
|
|
|
|
|
[ "${mounted_procfs:-}" = 1 ] && umount "$procfs" 2>/dev/null
|
|
|
|
|
[ "${insmod_cpuid:-}" = 1 ] && rmmod cpuid 2>/dev/null
|
|
|
|
@ -86,10 +87,11 @@ show_usage()
|
|
|
|
|
--batch nrpe produce machine readable output formatted for NRPE
|
|
|
|
|
--batch prometheus produce output for consumption by prometheus-node-exporter
|
|
|
|
|
|
|
|
|
|
--variant VARIANT specify which variant you'd like to check, by default all variants are checked
|
|
|
|
|
VARIANT can be one of 1, 2, 3, 3a, 4, l1tf, msbds, mfbds, mlpds, mdsum, taa, mcepsc, srbds
|
|
|
|
|
can be specified multiple times (e.g. --variant 2 --variant 3)
|
|
|
|
|
--cve [cve1,cve2,...] specify which CVE you'd like to check, by default all supported CVEs are checked
|
|
|
|
|
--variant VARIANT specify which variant you'd like to check, by default all variants are checked.
|
|
|
|
|
can be used multiple times (e.g. --variant 3a --variant l1tf)
|
|
|
|
|
for a list of supported VARIANT parameters, use --variant help
|
|
|
|
|
--cve CVE specify which CVE you'd like to check, by default all supported CVEs are checked
|
|
|
|
|
can be used multiple times (e.g. --cve CVE-2017-5753 --cve CVE-2020-0543)
|
|
|
|
|
--hw-only only check for CPU information, don't check for any variant
|
|
|
|
|
--no-hw skip CPU information and checks, if you're inspecting a kernel not to be run on this host
|
|
|
|
|
--vmm [auto,yes,no] override the detection of the presence of a hypervisor, default: auto
|
|
|
|
@ -350,7 +352,8 @@ is_cpu_affected()
|
|
|
|
|
variant_taa=''
|
|
|
|
|
variant_itlbmh=''
|
|
|
|
|
variant_srbds=''
|
|
|
|
|
variant_zenbleed=''
|
|
|
|
|
# Zenbleed if extremely AMD specific, look for "is_and" below:
|
|
|
|
|
variant_zenbleed=immune
|
|
|
|
|
|
|
|
|
|
if is_cpu_mds_free; then
|
|
|
|
|
[ -z "$variant_msbds" ] && variant_msbds=immune
|
|
|
|
@ -383,7 +386,6 @@ is_cpu_affected()
|
|
|
|
|
variant_mdsum=immune
|
|
|
|
|
variant_taa=immune
|
|
|
|
|
variant_srbds=immune
|
|
|
|
|
variant_zenbleed=immune
|
|
|
|
|
elif is_intel; then
|
|
|
|
|
# Intel
|
|
|
|
|
# https://github.com/crozone/SpectrePoC/issues/1 ^F E5200 => spectre 2 not affected
|
|
|
|
@ -459,7 +461,6 @@ is_cpu_affected()
|
|
|
|
|
_debug "is_cpu_affected: intel family < 6 is immune to l1tf"
|
|
|
|
|
[ -z "$variantl1tf" ] && variantl1tf=immune
|
|
|
|
|
fi
|
|
|
|
|
variant_zenbleed=immune
|
|
|
|
|
elif is_amd || is_hygon; then
|
|
|
|
|
# AMD revised their statement about variant2 => affected
|
|
|
|
|
# https://www.amd.com/en/corporate/speculative-execution
|
|
|
|
@ -476,7 +477,6 @@ is_cpu_affected()
|
|
|
|
|
variantl1tf=immune
|
|
|
|
|
|
|
|
|
|
# Zenbleed
|
|
|
|
|
variant_zenbleed=immune
|
|
|
|
|
amd_legacy_erratum "$(amd_model_range 0x17 0x30 0x0 0x4f 0xf)" && variant_zenbleed=vuln
|
|
|
|
|
amd_legacy_erratum "$(amd_model_range 0x17 0x60 0x0 0x7f 0xf)" && variant_zenbleed=vuln
|
|
|
|
|
amd_legacy_erratum "$(amd_model_range 0x17 0xa0 0x0 0xaf 0xf)" && variant_zenbleed=vuln
|
|
|
|
@ -585,7 +585,6 @@ is_cpu_affected()
|
|
|
|
|
_debug "is_cpu_affected: for cpu$i and so far, we have <$variant1> <$variant2> <$variant3> <$variant3a> <$variant4>"
|
|
|
|
|
done
|
|
|
|
|
variantl1tf=immune
|
|
|
|
|
variant_zenbleed=immune
|
|
|
|
|
fi
|
|
|
|
|
|
|
|
|
|
# we handle iTLB Multihit here (not linked to is_specex_free)
|
|
|
|
@ -859,6 +858,29 @@ show_header()
|
|
|
|
|
_info
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
# Family-Model-Stepping to CPUID
|
|
|
|
|
# prints CPUID in base-10 to stdout
|
|
|
|
|
fms2cpuid()
|
|
|
|
|
{
|
|
|
|
|
_family="$1"
|
|
|
|
|
_model="$2"
|
|
|
|
|
_stepping="$3"
|
|
|
|
|
|
|
|
|
|
if [ "$(( _family ))" -le 15 ]; then
|
|
|
|
|
_extfamily=0
|
|
|
|
|
_lowfamily=$(( _family ))
|
|
|
|
|
else
|
|
|
|
|
# when we have a family > 0xF, then lowfamily is stuck at 0xF
|
|
|
|
|
# and extfamily is ADDED to it (as in "+"), to ensure old software
|
|
|
|
|
# never sees a lowfamily < 0xF for newer families
|
|
|
|
|
_lowfamily=15
|
|
|
|
|
_extfamily=$(( (_family) - 15 ))
|
|
|
|
|
fi
|
|
|
|
|
_extmodel=$(( (_model & 0xF0 ) >> 4 ))
|
|
|
|
|
_lowmodel=$(( (_model & 0x0F ) >> 0 ))
|
|
|
|
|
echo $(( (_stepping & 0x0F) | (_lowmodel << 4) | (_lowfamily << 8) | (_extmodel << 16) | (_extfamily << 20) ))
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
[ -z "$HOME" ] && HOME="$(getent passwd "$(whoami)" | cut -d: -f6)"
|
|
|
|
|
mcedb_cache="$HOME/.mcedb"
|
|
|
|
|
update_fwdb()
|
|
|
|
@ -924,7 +946,9 @@ update_fwdb()
|
|
|
|
|
return 1
|
|
|
|
|
fi
|
|
|
|
|
sqlite3 "$mcedb_tmp" "ALTER TABLE \"Intel\" ADD COLUMN \"origin\" TEXT"
|
|
|
|
|
sqlite3 "$mcedb_tmp" "ALTER TABLE \"AMD\" ADD COLUMN \"origin\" TEXT"
|
|
|
|
|
sqlite3 "$mcedb_tmp" "UPDATE \"Intel\" SET \"origin\"='mce'"
|
|
|
|
|
sqlite3 "$mcedb_tmp" "UPDATE \"AMD\" SET \"origin\"='mce'"
|
|
|
|
|
|
|
|
|
|
echo OK "MCExtractor database revision $mcedb_revision"
|
|
|
|
|
|
|
|
|
@ -975,6 +999,48 @@ update_fwdb()
|
|
|
|
|
fi
|
|
|
|
|
echo DONE "(version $_intel_latest_date)"
|
|
|
|
|
|
|
|
|
|
# now parse the most recent linux-firmware amd-ucode README file
|
|
|
|
|
_info_nol "Fetching latest amd-ucode README from linux-firmware project... "
|
|
|
|
|
linuxfw_url="https://git.kernel.org/pub/scm/linux/kernel/git/firmware/linux-firmware.git/tree/amd-ucode/README"
|
|
|
|
|
linuxfw_tmp=$(mktemp -t smc-linuxfw-XXXXXX)
|
|
|
|
|
if command -v wget >/dev/null 2>&1; then
|
|
|
|
|
wget -q "$linuxfw_url" -O "$linuxfw_tmp"; ret=$?
|
|
|
|
|
elif command -v curl >/dev/null 2>&1; then
|
|
|
|
|
curl -sL "$linuxfw_url" -o "$linuxfw_tmp"; ret=$?
|
|
|
|
|
elif command -v fetch >/dev/null 2>&1; then
|
|
|
|
|
fetch -q "$linuxfw_url" -o "$linuxfw_tmp"; ret=$?
|
|
|
|
|
else
|
|
|
|
|
echo ERROR "please install one of \`wget\`, \`curl\` of \`fetch\` programs"
|
|
|
|
|
return 1
|
|
|
|
|
fi
|
|
|
|
|
if [ "$ret" != 0 ]; then
|
|
|
|
|
echo ERROR "error $ret while downloading linux-firmware README"
|
|
|
|
|
return $ret
|
|
|
|
|
fi
|
|
|
|
|
echo DONE
|
|
|
|
|
|
|
|
|
|
_info_nol "Parsing the README... "
|
|
|
|
|
nbfound=0
|
|
|
|
|
for line in $(grep -E 'Family=0x[0-9a-f]+ Model=0x[0-9a-f]+ Stepping=0x[0-9a-f]+: Patch=0x[0-9a-f]+' "$linuxfw_tmp" | tr " " ","); do
|
|
|
|
|
_debug "Parsing line $line"
|
|
|
|
|
_family=$( echo "$line" | grep -Eoi 'Family=0x[0-9a-f]+' | cut -d= -f2)
|
|
|
|
|
_model=$( echo "$line" | grep -Eoi 'Model=0x[0-9a-f]+' | cut -d= -f2)
|
|
|
|
|
_stepping=$(echo "$line" | grep -Eoi 'Stepping=0x[0-9a-f]+' | cut -d= -f2)
|
|
|
|
|
_version=$( echo "$line" | grep -Eoi 'Patch=0x[0-9a-f]+' | cut -d= -f2)
|
|
|
|
|
_version=$(printf "0x%08X" "$(( _version ))")
|
|
|
|
|
_cpuid=$(fms2cpuid "$_family" "$_model" "$_stepping")
|
|
|
|
|
_cpuid=$(printf "0x%08X" "$_cpuid")
|
|
|
|
|
_date="20000101"
|
|
|
|
|
_sqlstm="$(printf "INSERT INTO \"AMD\" (\"origin\",\"cpuid\",\"version\",\"yyyymmdd\") VALUES ('%s','%s','%s','%s');" "linux-firmware" "$(printf "%08X" "$_cpuid")" "$(printf "%08X" "$_version")" "$_date")"
|
|
|
|
|
_debug "family $_family model $_model stepping $_stepping cpuid $_cpuid"
|
|
|
|
|
_debug "$_sqlstm"
|
|
|
|
|
sqlite3 "$mcedb_tmp" "$_sqlstm"
|
|
|
|
|
nbfound=$((nbfound + 1))
|
|
|
|
|
unset _family _model _stepping _version _cpuid _date _sqlstm
|
|
|
|
|
done
|
|
|
|
|
echo "found $nbfound microcodes"
|
|
|
|
|
unset nbfound
|
|
|
|
|
|
|
|
|
|
dbversion="$mcedb_revision+i$_intel_latest_date"
|
|
|
|
|
|
|
|
|
|
if [ "$1" != builtin ] && [ -n "$previous_dbversion" ] && [ "$previous_dbversion" = "v$dbversion" ]; then
|
|
|
|
@ -1151,25 +1217,29 @@ while [ -n "${1:-}" ]; do
|
|
|
|
|
shift 2
|
|
|
|
|
elif [ "$1" = "--variant" ]; then
|
|
|
|
|
if [ -z "$2" ]; then
|
|
|
|
|
echo "$0: error: option --variant expects a parameter (1, 2, 3, 3a, 4 or l1tf)" >&2
|
|
|
|
|
echo "$0: error: option --variant expects a parameter (see --variant help)" >&2
|
|
|
|
|
exit 255
|
|
|
|
|
fi
|
|
|
|
|
case "$2" in
|
|
|
|
|
1) opt_cve_list="$opt_cve_list CVE-2017-5753"; opt_cve_all=0;;
|
|
|
|
|
2) opt_cve_list="$opt_cve_list CVE-2017-5715"; opt_cve_all=0;;
|
|
|
|
|
3) opt_cve_list="$opt_cve_list CVE-2017-5754"; opt_cve_all=0;;
|
|
|
|
|
3a) opt_cve_list="$opt_cve_list CVE-2018-3640"; opt_cve_all=0;;
|
|
|
|
|
4) opt_cve_list="$opt_cve_list CVE-2018-3639"; opt_cve_all=0;;
|
|
|
|
|
msbds) opt_cve_list="$opt_cve_list CVE-2018-12126"; opt_cve_all=0;;
|
|
|
|
|
mfbds) opt_cve_list="$opt_cve_list CVE-2018-12130"; opt_cve_all=0;;
|
|
|
|
|
mlpds) opt_cve_list="$opt_cve_list CVE-2018-12127"; opt_cve_all=0;;
|
|
|
|
|
mdsum) opt_cve_list="$opt_cve_list CVE-2019-11091"; opt_cve_all=0;;
|
|
|
|
|
l1tf) opt_cve_list="$opt_cve_list CVE-2018-3615 CVE-2018-3620 CVE-2018-3646"; opt_cve_all=0;;
|
|
|
|
|
taa) opt_cve_list="$opt_cve_list CVE-2019-11135"; opt_cve_all=0;;
|
|
|
|
|
mcepsc) opt_cve_list="$opt_cve_list CVE-2018-12207"; opt_cve_all=0;;
|
|
|
|
|
srbds) opt_cve_list="$opt_cve_list CVE-2020-0543"; opt_cve_all=0;;
|
|
|
|
|
help) echo "The following parameters are supported for --variant (can be used multiple times):";
|
|
|
|
|
echo "1, 2, 3, 3a, 4, msbds, mfbds, mlpds, mdsum, l1tf, taa, mcepsc, srbds, zenbleed";
|
|
|
|
|
exit 0;;
|
|
|
|
|
1) opt_cve_list="$opt_cve_list CVE-2017-5753"; opt_cve_all=0;;
|
|
|
|
|
2) opt_cve_list="$opt_cve_list CVE-2017-5715"; opt_cve_all=0;;
|
|
|
|
|
3) opt_cve_list="$opt_cve_list CVE-2017-5754"; opt_cve_all=0;;
|
|
|
|
|
3a) opt_cve_list="$opt_cve_list CVE-2018-3640"; opt_cve_all=0;;
|
|
|
|
|
4) opt_cve_list="$opt_cve_list CVE-2018-3639"; opt_cve_all=0;;
|
|
|
|
|
msbds) opt_cve_list="$opt_cve_list CVE-2018-12126"; opt_cve_all=0;;
|
|
|
|
|
mfbds) opt_cve_list="$opt_cve_list CVE-2018-12130"; opt_cve_all=0;;
|
|
|
|
|
mlpds) opt_cve_list="$opt_cve_list CVE-2018-12127"; opt_cve_all=0;;
|
|
|
|
|
mdsum) opt_cve_list="$opt_cve_list CVE-2019-11091"; opt_cve_all=0;;
|
|
|
|
|
l1tf) opt_cve_list="$opt_cve_list CVE-2018-3615 CVE-2018-3620 CVE-2018-3646"; opt_cve_all=0;;
|
|
|
|
|
taa) opt_cve_list="$opt_cve_list CVE-2019-11135"; opt_cve_all=0;;
|
|
|
|
|
mcepsc) opt_cve_list="$opt_cve_list CVE-2018-12207"; opt_cve_all=0;;
|
|
|
|
|
srbds) opt_cve_list="$opt_cve_list CVE-2020-0543"; opt_cve_all=0;;
|
|
|
|
|
zenbleed) opt_cve_list="$opt_cve_list CVE-2023-20593"; opt_cve_all=0;;
|
|
|
|
|
*)
|
|
|
|
|
echo "$0: error: invalid parameter '$2' for --variant, expected either 1, 2, 3, 3a, 4, l1tf, msbds, mfbds, mlpds, mdsum, taa, mcepsc or srbds" >&2;
|
|
|
|
|
echo "$0: error: invalid parameter '$2' for --variant, see --variant help for a list" >&2;
|
|
|
|
|
exit 255
|
|
|
|
|
;;
|
|
|
|
|
esac
|
|
|
|
@ -5939,6 +6009,7 @@ check_CVE_2023_20593_linux()
|
|
|
|
|
pvulnstatus "$cve" OK "your CPU vendor reported your CPU model as not affected"
|
|
|
|
|
elif [ -z "$msg" ]; then
|
|
|
|
|
# if msg is empty, sysfs check didn't fill it, rely on our own test
|
|
|
|
|
zenbleed_print_vuln=0
|
|
|
|
|
if [ "$opt_live" = 1 ]; then
|
|
|
|
|
if [ "$fp_backup_fix" = 1 ] && [ "$cpu_ucode_zenbleed" = 1 ]; then
|
|
|
|
|
# this should never happen, but if it does, it's interesting to know
|
|
|
|
@ -5948,7 +6019,7 @@ check_CVE_2023_20593_linux()
|
|
|
|
|
elif [ "$fp_backup_fix" = 1 ]; then
|
|
|
|
|
pvulnstatus $cve OK "Your kernel mitigates Zenbleed"
|
|
|
|
|
else
|
|
|
|
|
pvulnstatus $cve VULN "Your kernel is too old to mitigate Zenbleed and your CPU microcode doesn't mitigate it either"
|
|
|
|
|
zenbleed_print_vuln=1
|
|
|
|
|
fi
|
|
|
|
|
else
|
|
|
|
|
if [ "$cpu_ucode_zenbleed" = 1 ]; then
|
|
|
|
@ -5956,9 +6027,19 @@ check_CVE_2023_20593_linux()
|
|
|
|
|
elif [ -n "$kernel_zenbleed" ]; then
|
|
|
|
|
pvulnstatus $cve OK "Your kernel mitigates Zenbleed"
|
|
|
|
|
else
|
|
|
|
|
pvulnstatus $cve VULN "Your kernel is too old to mitigate Zenbleed and your CPU microcode doesn't mitigate it either"
|
|
|
|
|
zenbleed_print_vuln=1
|
|
|
|
|
fi
|
|
|
|
|
fi
|
|
|
|
|
if [ "$zenbleed_print_vuln" = 1 ]; then
|
|
|
|
|
pvulnstatus $cve VULN "Your kernel is too old to mitigate Zenbleed and your CPU microcode doesn't mitigate it either"
|
|
|
|
|
explain "Your CPU vendor may have a new microcode for your CPU model that mitigates this issue (refer to the hardware section above).\n " \
|
|
|
|
|
"Otherwise, the Linux kernel is able to mitigate this issue regardless of the microcode version you have, but in this case\n " \
|
|
|
|
|
"your kernel is too old to support this, your Linux distribution vendor might have a more recent version you should upgrade to.\n " \
|
|
|
|
|
"Note that either having an up to date microcode OR an up to date kernel is enough to mitigate this issue.\n " \
|
|
|
|
|
"To manually mitigate the issue right now, you may use the following command: \`wrmsr -a 0xc0011029 \$((\$(rdmsr -c 0xc0011029) | (1<<9)))\`,\n " \
|
|
|
|
|
"however note that this manual mitigation will only be active until the next reboot."
|
|
|
|
|
fi
|
|
|
|
|
unset zenbleed_print_vuln
|
|
|
|
|
else
|
|
|
|
|
pvulnstatus $cve "$status" "$msg"
|
|
|
|
|
fi
|
|
|
|
@ -6057,7 +6138,7 @@ exit 0 # ok
|
|
|
|
|
# The builtin version follows, but the user can download an up-to-date copy (to be stored in his $HOME) by using --update-fwdb
|
|
|
|
|
# To update the builtin version itself (by *modifying* this very file), use --update-builtin-fwdb
|
|
|
|
|
|
|
|
|
|
# %%% MCEDB v270+i20230614
|
|
|
|
|
# %%% MCEDB v271+i20230614
|
|
|
|
|
# I,0x00000611,0x00000B27,19961218
|
|
|
|
|
# I,0x00000612,0x000000C6,19961210
|
|
|
|
|
# I,0x00000616,0x000000C6,19961210
|
|
|
|
@ -6395,7 +6476,8 @@ exit 0 # ok
|
|
|
|
|
# I,0x000B06E0,0x00000010,20221219
|
|
|
|
|
# I,0x000B06F2,0x0000002C,20230104
|
|
|
|
|
# I,0x000B06F5,0x0000002C,20230104
|
|
|
|
|
# I,0x000C06F1,0x20000270,20230221
|
|
|
|
|
# I,0x000C06F1,0x21000030,20230410
|
|
|
|
|
# I,0x000C06F2,0x21000030,20230410
|
|
|
|
|
# A,0x00000F00,0x02000008,20070614
|
|
|
|
|
# A,0x00000F01,0x0000001C,20021031
|
|
|
|
|
# A,0x00000F10,0x00000003,20020325
|
|
|
|
@ -6419,13 +6501,17 @@ exit 0 # ok
|
|
|
|
|
# A,0x00100F00,0x01000020,20070326
|
|
|
|
|
# A,0x00100F20,0x010000CA,20100331
|
|
|
|
|
# A,0x00100F22,0x010000C9,20100331
|
|
|
|
|
# A,0x00100F2A,0x01000084,20000101
|
|
|
|
|
# A,0x00100F40,0x01000085,20080501
|
|
|
|
|
# A,0x00100F41,0x010000DB,20111024
|
|
|
|
|
# A,0x00100F42,0x01000092,20081021
|
|
|
|
|
# A,0x00100F43,0x010000C8,20100311
|
|
|
|
|
# A,0x00100F52,0x010000DB,20000101
|
|
|
|
|
# A,0x00100F53,0x010000C8,20000101
|
|
|
|
|
# A,0x00100F62,0x010000C7,20100311
|
|
|
|
|
# A,0x00100F80,0x010000DA,20111024
|
|
|
|
|
# A,0x00100F81,0x010000D9,20111012
|
|
|
|
|
# A,0x00100F91,0x010000D9,20000101
|
|
|
|
|
# A,0x00100FA0,0x010000DC,20111024
|
|
|
|
|
# A,0x00120F00,0x03000002,20100324
|
|
|
|
|
# A,0x00200F30,0x02000018,20070921
|
|
|
|
@ -6475,18 +6561,18 @@ exit 0 # ok
|
|
|
|
|
# A,0x00820F00,0x08200002,20180214
|
|
|
|
|
# A,0x00820F01,0x08200103,20190417
|
|
|
|
|
# A,0x00830F00,0x08300027,20190401
|
|
|
|
|
# A,0x00830F10,0x08301072,20220215
|
|
|
|
|
# A,0x00830F10,0x0830107A,20230517
|
|
|
|
|
# A,0x00850F00,0x08500004,20180212
|
|
|
|
|
# A,0x00860F00,0x0860000E,20200127
|
|
|
|
|
# A,0x00860F01,0x08600109,20220328
|
|
|
|
|
# A,0x00860F81,0x08608104,20220328
|
|
|
|
|
# A,0x00870F00,0x08700004,20181206
|
|
|
|
|
# A,0x00870F10,0x08701030,20220328
|
|
|
|
|
# A,0x008A0F00,0x08A00006,20220322
|
|
|
|
|
# A,0x008A0F00,0x08A00008,20230615
|
|
|
|
|
# A,0x00A00F00,0x0A000033,20200413
|
|
|
|
|
# A,0x00A00F10,0x0A001078,20230117
|
|
|
|
|
# A,0x00A00F11,0x0A0011CE,20230114
|
|
|
|
|
# A,0x00A00F12,0x0A001231,20230117
|
|
|
|
|
# A,0x00A00F10,0x0A001079,20230609
|
|
|
|
|
# A,0x00A00F11,0x0A0011D1,20230710
|
|
|
|
|
# A,0x00A00F12,0x0A001234,20230710
|
|
|
|
|
# A,0x00A00F80,0x0A008003,20211015
|
|
|
|
|
# A,0x00A00F82,0x0A008205,20220414
|
|
|
|
|
# A,0x00A10F00,0x0A10004B,20220309
|
|
|
|
|