{"record":{"id":"0973dd0c6f532eb1","repo":"denoland/deno","slug":"invalid-authentication-tag-length-tagbytelength","errorCode":null,"errorMessage":"Invalid authentication tag length: ${tagByteLength}","messagePattern":"Invalid authentication tag length: (.+?)","errorType":"exception","errorClass":"TypeError","httpStatus":null,"severity":"error","filePath":"ext/node/polyfills/internal/crypto/cipher.ts","lineNumber":658,"sourceCode":"\nDecipheriv.prototype.setAuthTag = function (\n  buffer: any,\n  _encoding?: string,\n) {\n  if (this._authTag) {\n    throw new ERR_CRYPTO_INVALID_STATE(\"setAuthTag\");\n  }\n  // When no explicit `authTagLength` was given at decipher creation time, a\n  // GCM authentication tag must be the full 128 bits (16 bytes); shorter tags\n  // are only accepted when `authTagLength` is set. This used to be the DEP0182\n  // deprecation warning and is now a hard error (matching Node.js).\n  // deno-lint-ignore deno-internal/prefer-primordials -- `buffer` may be Buffer/TypedArray/DataView\n  const tagByteLength = buffer.byteLength;\n  if (\n    this._isGcmMode && this._authTagLength === -1 &&\n    tagByteLength !== 16\n  ) {\n    throw new TypeError(\n      `Invalid authentication tag length: ${tagByteLength}`,\n    );\n  }\n  // deno-lint-ignore deno-internal/prefer-primordials -- `buffer` may be Buffer/TypedArray/DataView\n  op_node_decipheriv_auth_tag(this._context, buffer.byteLength);\n  this._authTag = buffer;\n  return this;\n};\n\nDecipheriv.prototype.setAutoPadding = function (autoPadding?: boolean) {\n  this._autoPadding = Boolean(autoPadding);\n  this._cache.lastChunkIsNonZero = this._autoPadding;\n  return this;\n};\n\nDecipheriv.prototype.update = function (\n  data: string | Buffer | ArrayBufferView,\n  inputEncoding?: any,","sourceCodeStart":640,"sourceCodeEnd":676,"githubUrl":"https://github.com/denoland/deno/blob/9ad36f7a2cce60488e6ec52283efb32efddaf93a/ext/node/polyfills/internal/crypto/cipher.ts#L640-L676","documentation":"For GCM, when createDecipheriv() received no explicit authTagLength option (_authTagLength === -1), the authentication tag must be exactly 16 bytes (128 bits); any other tagByteLength throws TypeError 'Invalid authentication tag length: N'. This was Node deprecation DEP0182 and is now a hard error — the polyfill matches Node's current behavior. Shorter tags (4-15 bytes) are legal only when authTagLength was declared at construction.","triggerScenarios":"createDecipheriv('aes-128-gcm', key, iv) followed by setAuthTag(tag.subarray(0, 8)) — a truncated tag without a declared length; interop with peers (Java/GnuTLS/BoringSSL) configured for short GCM tags; accidentally passing ciphertext, IV, or a mis-sliced portion of the payload instead of the tag.","commonSituations":"Upgrading Node/Deno where the DEP0182 warning became a hard error; splitting payload||tag blobs with an off-by-one slice length; protocols negotiated for 96-bit tags while the decrypt code assumes defaults.","solutions":["Declare the expected length at construction: createDecipheriv('aes-128-gcm', key, iv, { authTagLength: tag.length }).","Or make the encrypting side emit full 16-byte tags.","Verify you are passing the actual tag: check slice offsets when splitting payload|tag, and assert tag.length matches the protocol."],"exampleFix":"// before\nconst d = crypto.createDecipheriv('aes-128-gcm', key, iv);\nd.setAuthTag(blob.subarray(blob.length - 8)); // 8-byte tag, no authTagLength -> TypeError\n\n// after\nconst tagLen = 8;\nconst d = crypto.createDecipheriv('aes-128-gcm', key, iv, { authTagLength: tagLen });\nd.setAuthTag(blob.subarray(blob.length - tagLen));","handlingStrategy":"validation","validationCode":"function gcmDecipher(key: Buffer, iv: Buffer, tag: Buffer): crypto.DecipherGCM {\n  if (tag.length !== 16)\n    return crypto.createDecipheriv('aes-128-gcm', key, iv, { authTagLength: tag.length });\n  return crypto.createDecipheriv('aes-128-gcm', key, iv);\n}\n// gcmDecipher(key, iv, tag).setAuthTag(tag) never throws the length TypeError","typeGuard":null,"tryCatchPattern":"try { d.setAuthTag(tag); } catch (e) { if (e.message.startsWith('Invalid authentication tag length')) { d = crypto.createDecipheriv(algo, key, iv, { authTagLength: tag.length }); d.setAuthTag(tag); } else throw e; }","preventionTips":["Always pass { authTagLength: tag.length } when the protocol uses non-16-byte GCM tags.","Standardize on full 16-byte tags unless a spec forces otherwise.","Unit-test tag slicing offsets when splitting payload||tag blobs; assert tag.length matches the negotiated value."],"tags":["crypto","decipher","aead","auth-tag","gcm","node-compat"],"backgroundTag":"invalid-auth-tag-length","analyzedSha":"9ad36f7a2cce60488e6ec52283efb32efddaf93a","analyzedAt":"2026-08-20T13:07:44.778Z","contentChangedAt":"2026-08-20T13:07:44.778Z","schemaVersion":2},"datasetVersion":"2026-09-14T00:17:10.932Z"}