第三方工具安全性各有不同,风险自负。
以上工具都支持第三方的 Steam 二步验证。
虽然 Steam 的字母数字混合五位验证码看起来和别的 OTP Authenticator 高贵,其实都是一种东西。
即基于 Time-based One-time Password 算法的一次性密码生成器,又称:
- 两步验证
- 二步验证
- 双重验证
- 双因素验证
- 多因素验证
- 虚拟 MFA(我只看到过阿里这么叫)
- 动态令牌
- 2FA
- Two-Factor Authentication
- Multi-Factor Authentication
- OTP(One Time Password)
花名很多嘛。
它家只要有 shared_secret
和 identity_secret
就允许导入。
也就是说,最少:
1
2
3
4
| {
"shared_secret": "[key_secret_1]",
"identity_secret": "[key_secret_2]"
}
|
就可以正常运作了。
但这样的话,比较关键的 恢复代码
以及 设备 ID
等额外信息都没有。
所以还是推荐该有的都加上,新建文本文档,命名为 min.example.maFile
:
1
2
3
4
5
6
7
8
9
| {
"account_name": "[your_steam_username]",
"revocation_code": "[revocation_code]",
"device_id": "android:[phone_uuid]",
"uri": "otpauth://totp/Steam:[your_steam_username]?secret=[totp_secret]&issuer=Steam",
"shared_secret": "[key_secret_1]",
"identity_secret": "[key_secret_2]",
"steamid": "[your_steam_64bit_id]"
}
|
除了最关键的两个密钥之外比较关键的是:revocation_code
- 恢复代码。
其次是 uri
里面有 [totp_secret]
,别的都是锦上添花的东西。
导出的格式类似 WinAuth.example.maFile
:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
| {
"account_name": "[your_steam_username]",
"revocation_code": "[revocation_code]",
"device_id": "android:[phone_uuid]",
"uri": "otpauth://totp/Steam:[your_steam_username]?secret=[totp_secret]&issuer=Steam",
"shared_secret": "[key_secret_1]",
"identity_secret": "[key_secret_2]",
"serial_number": "[serial_number]",
"server_time": "[server_time]",
"token_gid": "[token_gid]",
"secret_1": "[secret_1]",
"status": 1,
"steamguard_scheme": "2",
"steamid": "[your_steam_64bit_id]"
}
|
导出的格式类似 SDA.example.maFile
:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
| {
"account_name": "[your_steam_username]",
"revocation_code": "[revocation_code]",
"device_id": "android:[phone_uuid]",
"uri": "otpauth://totp/Steam:[your_steam_username]?secret=[totp_secret]&issuer=Steam",
"shared_secret": "[key_secret_1]",
"identity_secret": "[key_secret_2]",
"serial_number": "[serial_number]",
"server_time": "[server_time]",
"token_gid": "[token_gid]",
"secret_1": "[secret_1]",
"status": 1,
"fully_enrolled": true,
"Session": {
"SessionID": "[string]",
"SteamLogin": "[string]",
"SteamLoginSecure": "[string]",
"WebCookie": "[string]",
"OAuthToken": "[string]",
"SteamID": "[string]"
}
}
|
我是 KeePass 用户,TOTP 插件还蛮多的,我用的 KeeTrayTOTP。
用上面的软件绑定手机令牌后导出,用文本编辑器打开 .maFile
文件,会有 uri
项:
"uri": "otpauth://totp/Steam:[your_steam_username]?secret=[totp_secret]&issuer=Steam",
记录下 [totp_secret]
,这个就是 Steam 令牌作为 TOTP 工具时的序列号。
之前用 Python 和 Go 复现过 Steam 令牌算法,其实就是标准的 TOTP 算法,不过最后生成验证码的时候用了一个取巧的小 trick。序列还是那个序列,但把原本的 6 位或 8 位纯数字验证码 hash 成了 5 位字母数字混合验证码而已。
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
| from time import time
import pyotp
from hmac import new as hmac_sha1
from struct import pack, unpack
def generate_steam_two_factor_code(secret: str):
totp = pyotp.parse_uri(f"otpauth://totp/Steam:whatever?secret={secret}&issuer=Steam")
# pyotp.OTP.byte_secret(totp) == base64.b64decode(shared_secret)
hasher = hmac_sha1(pyotp.OTP.byte_secret(totp), pack('>Q', int(time()) // 30), totp.digest)
hmac_hash = bytearray(hasher.digest())
start = ord(hmac_hash[19:20]) & 0xF
code_num = unpack('>I', hmac_hash[start:start + 4])[0] & 0x7fffffff
charset = '23456789BCDFGHJKMNPQRTVWXY'
steam_code = ''
for _ in range(5):
code_num, i = divmod(code_num, len(charset))
steam_code += charset[i]
return steam_code
|