跳转至

http.frm.auth

认证三件套(P6-C;cookie 解析/签发 + HMAC 签名 会话令牌 + JWT HS256 + own 盒会话存储)

语义登记(v1 口径,偏离/志向逐条):

① Cookie 面:auth_cookie_get = Cookie 头 "a=b; c=d" 名精确匹配取值 (零解码 —— 值域即签发域 [A-Za-z0-9_-.],percent/plus 解码登记缺席, 从严;DQuote 包裹值(RFC 6265 §5.2 容许形)登记缺席)。auth_cookie_set = Set-Cookie 行构造:属性序【恒】 Path=/; HttpOnly?; Max-Age=?; SameSite=Lax(csrf.ct Task-3 对齐登记:Path 前置、SameSite=Lax 收尾, 会话版增 HttpOnly/Max-Age 居中 —— HttpOnly 先、Max-Age 后,序登记); maxage < 0 = 会话 cookie(不发 Max-Age);maxage >= 0 恒发(Max-Age=0 = 即刻过期删除面,RFC 6265 §5.2.2)。构造期校验(注入面封口):name = RFC 9110 tchar 域 1..64,value = cookie-octet 窄域(0x21..0x7E 去 DQUOTE/逗号/分号/反斜杠)0..4096 —— name/value 任一出域 → 返回 "" (空行 = 构造拒;CR/LF/控制字节不可达 → 头走私面封口,csrf 同口径)。

② 签名会话令牌(无状态;own 盒存储之对偶):auth_tok_issue(key, uid, now, ttl) → tok = uid "." exp "." hex(HMAC-SHA256(key, uid "." exp)) (csrf 签名对同构,值携过期 —— exp = now+ttl unix_ms 十进制)。校验 auth_tok_verify(key, tok, now):形(恰两点、域、exp 数、sig 64 hex) → 签名重算恒时比较(csrf cr_ct_eq 算术平方累计同式,本模块私铸 —— 直引即同叶双径)→ 过期判(now >= exp 拒,RFC 7519 §4.1.4「须早于」 字面口径,jwt exp 同规)。uid 域 = [A-Za-z0-9_-]{1,64}(cookie 安全)。

③ JWT HS256(RFC 7515/7519):header 钉死 {"alg":"HS256","typ":"JWT"} —— 校验面对收报首段(b64url)与钉形常量 auth_jwt_hdr_b64 【整串字节 等值】判,alg=none/RS256/缺 typ/任意增删字段一概异形即拒 (auth_err_alg=9;alg 混淆防护 = 钉形即防护,自定义 header(kid 等)列 志向;常量与字面 header 的编码等值有 inline 测试互钉)。签名段 = base64url(HMAC-SHA256(key, header_b64 "." payload_b64))(无填充 RFC 7515;字母表 -_);b64url 自出 lane-b64(ws.ct 先例:std/enc b64_decode 入 C8 printable 域且标准字母表,不取)。恒时比较在【编码域】 进行(重算期待 b64url 串 vs 收报 sig 段,解码不需要)。载荷 b64url 解码 = List[I32] 字节道(router.ct body 绑定字节道登记同向;Str 表格构建面 —— byte_slice 可印表 —— 载不下 123 '{' 字节,故 claims 扫描直接走 字节,任意字节载荷可解)。claims 扫描 = 平面字节扫 "name" : 后 整数 token(首现胜出/重复键登记;字符串值内引号假象登记 v1 限 —— 载荷 恒 composition 层经 std/json write 面产出)。exp/iat/nbf 判: exp 缺省可过(RFC 7519 不强制;required 模式列志向)/ now >= exp 拒 / nbf now < nbf 拒(§4.1.5「on or after」)/ iat 恒 iat <= now(零钟差 从严档,登记)。RS256 = 志向(纯层无 RSA;登记)。

④ own 盒会话存储(有状态对偶;外置 Redis 列 P8 注记):SessStore = 显式值状态(8 槽定容;组合层持有并以值重建下传 —— limit.ct LimBkt 先例;纯层无全局无可变量)。put = upsert(同 sid 原槽替换;新 sid 落 首空槽,次占过期槽 —— now >= e 判;满 → why 14 原样返回)。get = 1 命中有效(now < e)/ 0 miss / -1 过期(组合层决定删)。del/gc = 值重建。sid 熵源 = composition 层注入(uuid_v4/随机 —— csrf nonce 同 口径,纯层无熵);时钟恒注入参数 now(unix_ms)—— limit.ct 确定性 先例,真钟装配归组合层(std.time Clock 出面)。

注入面:Set-Cookie 值/name 恒经构造域校验(①);tok/jwt 值域 = 签发 域(token 字符);Retry 类无。请求侧取值面产出只进校验比较面。

use 面:std.crypto 单叶(hmac_sha256/bytes_to_hex —— csrf.ct 同款; 消费方若自用 std.crypto 再 use 本模块 = 同叶双径 E5020,禁)。常时 比较/字位面私铸不导(防菱形);【禁】use std.json(claims 平面字节扫, 见 ③)—— body.ct 另持 json 叶,两模块可在同一 fixture 并用而 json 单径不菱形。byte_at/byte_slice = 内建(零 use)。【utf8_enc 内建禁用】 P6-C 实证:解释臂恒产 U+FFFD 替换列(0xEF 0xBF 0xBD),emit 臂真编码 —— 双臂语义劈叉,单字节 Str 构建恒走 au_ch 表格面(csrf/ws 同式)。

pub struct

struct AuthTok

Field Type
ok I64
why I64
tok Str

struct TokVer

Field Type
rc I64
why I64
uid Str

struct AuthClaim

claims 平面扫描结果(k: 1 命中 / 0 缺 / -1 命中但值非整数形;首现胜出)

Field Type
k I64
v I64

struct JwtVer

Field Type
rc I64
why I64

struct SessStore

Field Type
n I64
e0 I64
e1 I64
e2 I64
e3 I64
e4 I64
e5 I64
e6 I64
e7 I64
s0 Str
s1 Str
s2 Str
s3 Str
s4 Str
s5 Str
s6 Str
s7 Str
r0 Str
r1 Str
r2 Str
r3 Str
r4 Str
r5 Str
r6 Str
r7 Str

struct SessPut

Field Type
ok I64
why I64
st SessStore

struct SessGet

Field Type
rc I64
user Str

pub fn

Signature Returns Description
auth_err_ok() I64 —
auth_err_empty() I64 —
auth_err_shape() I64 —
auth_err_uid() I64 —
auth_err_expnum() I64 —
auth_err_sigform() I64 —
auth_err_sig() I64 —
auth_err_expired() I64 —
auth_err_b64() I64 —
auth_err_alg() I64 —
auth_err_nbf() I64 —
auth_err_iat() I64 —
auth_err_claim() I64 —
auth_err_full() I64 —
auth_cookie_get(cookie_hdr: Str, name: Str) Str Cookie 头值 "a=b; c=d" → 名精确匹配值(无 → "";首匹配胜出;零解码)
auth_cookie_set(name: Str, value: Str, maxage: I64, httponly: I64) Str Set-Cookie 行(属性序登记见头注①;CRLF 自备)。构造期校验:任一出域
→ ""(注入面封口:CR/LF/控制字节/裸逗号分号反斜杠 DQUOTE 不可达)。
maxage < 0 = 会话 cookie(无 Max-Age);>= 0 恒发(0 = 删除面)。
at_ok(t: AuthTok) I64 —
at_why(t: AuthTok) I64 —
at_tok(t: AuthTok) Str —
auth_tok_issue(key: Str, uid: Str, now: I64, ttl: I64) AuthTok 签发:tok = uid "." exp "." hex(HMAC-SHA256(key, uid "." exp))
tv_rc(v: TokVer) I64 —
tv_why(v: TokVer) I64 —
tv_uid(v: TokVer) Str —
auth_tok_verify(key: Str, tok: Str, now: I64) TokVer 校验:形 → 签名重算恒时比较 → 过期(now >= exp 拒,RFC 7519 §4.1.4 口径)
auth_b64url_encode(src: Str) Str b64url 编码(入参任意字节面 —— byte_at 逐字节,出参恒 ASCII;无填充)
auth_jwt_hdr() Str 钉死 JWT header(alg 混淆防护 = 整串字节等值钉形判,头注③)
ac_k(c: AuthClaim) I64 —
ac_v(c: AuthClaim) I64 —
auth_jwt_claim(payload: Str, name: Str) AuthClaim 公开面(载荷 Str 域;composition 侧查询)—— 字节道同一扫描
auth_jwt_sign(key: Str, payload: Str) AuthTok JWT 签发(结果面 = AuthTok 复用,at_* getter):tok = b64u(hdr) "."
b64u(payload) "." b64u(HMAC-SHA256(key, hdr_b64 "." pay_b64))(载荷逐字
签入,本模块不校验载荷 JSON —— composition 层经 std/json write 面产出,
登记头注③)
auth_jwt_hdr_b64() Str 钉死 header 的 b64url 形(常量;校验面以收报首段整串等值钉形判 ——
alg 混淆防护:alg=none/HS512/RS256/字段增删一概异形即拒)
jwt_rc(v: JwtVer) I64 —
jwt_why(v: JwtVer) I64 —
auth_jwt_verify(key: Str, tok: Str, now: I64) JwtVer 校验序(登记):空/形 → b64url 三段形 → header 钉形(整串等值,alg 混淆
拒)→ 签名重算恒时比较(编码域)→ 载荷解码(字节道)→ exp → nbf →
iat。claims 皆缺省可过(RFC 7519 不强制;required 模式列志向)。
auth_sess_cap() I64 —
auth_sess_new() SessStore —
sp_ok(p: SessPut) I64 —
sp_why(p: SessPut) I64 —
sp_st(p: SessPut) SessStore —
auth_sess_put(t: SessStore, sid: Str, user: Str, now: I64, ttl: I64) SessPut upsert:同 sid 原槽替换;新 sid 落首空槽,次占首个过期槽(now >= e);
满 → ok=0/why=14 原样返回(逐出策略归组合层)
sg_rc(g: SessGet) I64 —
sg_user(g: SessGet) Str —
auth_sess_get(t: SessStore, sid: Str, now: I64) SessGet 取:1 命中有效(now < e)/ 0 miss / -1 过期(删否归组合层)
auth_sess_del(t: SessStore, sid: Str) SessStore 删(不存在原样返回)
auth_sess_gc(t: SessStore, now: I64) SessStore 清扫过期(now >= e 全删;组合层周期驱动的便捷面)
auth_sess_len(t: SessStore) I64 活跃会话数