{"record":{"id":"d39904663a9fe19a","repo":"slackhq/nebula","slug":"unable-to-login-error-w","errorCode":null,"errorMessage":"unable to login. error: %w","messagePattern":"unable to login\\. error: %w","errorType":"exception","errorClass":null,"httpStatus":null,"severity":"error","filePath":"pkclient/pkclient_cgo.go","lineNumber":69,"sourceCode":"\tclient := &PKClient{\n\t\tmodule: module,\n\t\tid:     []byte(id),\n\t\tlabel:  []byte(label),\n\t}\n\n\tclient.session, err = slots[slotIdx].OpenWriteSession()\n\tif err != nil {\n\t\tmodule.Destroy()\n\t\treturn nil, fmt.Errorf(\"failed to open session on slot %d\", slotId)\n\t}\n\n\tif len(pin) != 0 {\n\t\terr = client.session.Login(pin)\n\t\tif err != nil {\n\t\t\t// ignore \"already logged in\"\n\t\t\tif !errors.Is(err, pkcs11.Error(256)) {\n\t\t\t\t_ = client.session.Close()\n\t\t\t\treturn nil, fmt.Errorf(\"unable to login. error: %w\", err)\n\t\t\t}\n\t\t}\n\t}\n\n\t// Make sure the hsm has a private key for deriving\n\tclient.privKeyObj, err = client.findDeriveKey(client.id, client.label, true)\n\tif err != nil {\n\t\t_ = client.Close() //log out, close session, destroy module\n\t\treturn nil, fmt.Errorf(\"failed to find private key for deriving: %w\", err)\n\t}\n\n\treturn client, nil\n}\n\n// Close cleans up properly and logs out\nfunc (c *PKClient) Close() error {\n\tvar err error = nil\n\tif c.session != nil {","sourceCodeStart":51,"sourceCodeEnd":87,"githubUrl":"https://github.com/slackhq/nebula/blob/dd8f660c0ac37903ec4080ca4d3c861ba9342ceb/pkclient/pkclient_cgo.go#L51-L87","documentation":"New() failed to login to the token with the provided PIN; the session is closed and the pkcs11 error is wrapped with %w. The library deliberately rethrows except for pkcs11 error 256 (CKR_USER_ALREADY_LOGGED_IN), which is tolerated. This means the token rejected authentication.","triggerScenarios":"Calling New() with a non-empty pin when session.Login(pin) returns an error other than pkcs11.Error(256): wrong PIN, CKR_PIN_LOCKED after repeated failures, CKR_USER_PIN_NOT_INITIALIZED, or login to a slot with no user credentials.","commonSituations":"Expired or mistyped PIN in config; account locked from previous attempts; PIN configured for a different token; HSM requiring SO login first.","solutions":["Verify the PIN is correct for the selected token/slot","If the PIN is locked, unlock/reset it with the vendor tool (or wait per policy)","If no auth is needed, pass an empty pin so Login is skipped","Confirm slotId points at the token the PIN belongs to","Test the PIN independently with pkcs11-tool --login --pin"],"exampleFix":"// before\npkcs11_pin: \"1234\"\n// after\npkcs11_pin: \"correct-current-pin\"","handlingStrategy":"try-catch","validationCode":"// verify the PIN by logging in on a scratch session before New()\nctx := pkcs11.New(modulePath); ctx.Initialize()\nsession, _ := ctx.OpenSession(slot, pkcs11.CKF_SERIAL_SESSION|pkcs11.CKF_RW_SESSION)\nif err := ctx.Login(session, pkcs11.CKU_USER, pin); err != nil {\n    return fmt.Errorf(\"PIN rejected: %w\", err)\n}","typeGuard":null,"tryCatchPattern":"client, err := pkclient.New(hsmPath, slot, pin, id, label)\nif err != nil {\n    var p11err pkcs11.Error\n    if errors.As(err, &p11err) && uint(p11err) == 0xA0+0x20 { // CKR_PIN_LOCKED (163/0x000000A0 family)\n        return errors.New(\"PIN locked; unlock with vendor tool before retrying\")\n    }\n    if strings.Contains(err.Error(), \"unable to login\") {\n        return fmt.Errorf(\"check PIN for slot %d: %w\", slot, err)\n    }\n    return err\n}","preventionTips":["Store the PIN in a secret manager, not plaintext config","Verify the PIN with pkcs11-tool --login before deploy","Handle CKR_PIN_LOCKED by resetting, not retrying","Use an empty pin only when the token genuinely needs no login","Confirm the PIN belongs to the selected slot's token"],"tags":["pkcs11","hsm","authentication","pin"],"backgroundTag":"hsm-login-failed","analyzedSha":"dd8f660c0ac37903ec4080ca4d3c861ba9342ceb","analyzedAt":"2026-09-03T11:13:55.444Z","contentChangedAt":"2026-09-03T11:13:55.444Z","schemaVersion":2},"datasetVersion":"2026-09-10T17:17:09.494Z"}