summaryrefslogtreecommitdiff
path: root/vendor/github.com/danieljoos
diff options
context:
space:
mode:
authormo khan <mo@mokhan.ca>2025-07-22 17:35:49 -0600
committermo khan <mo@mokhan.ca>2025-07-22 17:35:49 -0600
commit20ef0d92694465ac86b550df139e8366a0a2b4fa (patch)
tree3f14589e1ce6eb9306a3af31c3a1f9e1af5ed637 /vendor/github.com/danieljoos
parent44e0d272c040cdc53a98b9f1dc58ae7da67752e6 (diff)
feat: connect to spicedb
Diffstat (limited to 'vendor/github.com/danieljoos')
-rw-r--r--vendor/github.com/danieljoos/wincred/.gitattributes1
-rw-r--r--vendor/github.com/danieljoos/wincred/.gitignore25
-rw-r--r--vendor/github.com/danieljoos/wincred/LICENSE21
-rw-r--r--vendor/github.com/danieljoos/wincred/README.md145
-rw-r--r--vendor/github.com/danieljoos/wincred/conversion.go116
-rw-r--r--vendor/github.com/danieljoos/wincred/conversion_unsupported.go11
-rw-r--r--vendor/github.com/danieljoos/wincred/sys.go148
-rw-r--r--vendor/github.com/danieljoos/wincred/sys_unsupported.go36
-rw-r--r--vendor/github.com/danieljoos/wincred/types.go69
-rw-r--r--vendor/github.com/danieljoos/wincred/wincred.go114
10 files changed, 686 insertions, 0 deletions
diff --git a/vendor/github.com/danieljoos/wincred/.gitattributes b/vendor/github.com/danieljoos/wincred/.gitattributes
new file mode 100644
index 0000000..d207b18
--- /dev/null
+++ b/vendor/github.com/danieljoos/wincred/.gitattributes
@@ -0,0 +1 @@
+*.go text eol=lf
diff --git a/vendor/github.com/danieljoos/wincred/.gitignore b/vendor/github.com/danieljoos/wincred/.gitignore
new file mode 100644
index 0000000..6142c06
--- /dev/null
+++ b/vendor/github.com/danieljoos/wincred/.gitignore
@@ -0,0 +1,25 @@
+# Compiled Object files, Static and Dynamic libs (Shared Objects)
+*.o
+*.a
+*.so
+
+# Folders
+_obj
+_test
+
+# Architecture specific extensions/prefixes
+*.[568vq]
+[568vq].out
+
+*.cgo1.go
+*.cgo2.c
+_cgo_defun.c
+_cgo_gotypes.go
+_cgo_export.*
+
+_testmain.go
+
+*.exe
+*.test
+
+coverage.txt
diff --git a/vendor/github.com/danieljoos/wincred/LICENSE b/vendor/github.com/danieljoos/wincred/LICENSE
new file mode 100644
index 0000000..2f436f1
--- /dev/null
+++ b/vendor/github.com/danieljoos/wincred/LICENSE
@@ -0,0 +1,21 @@
+The MIT License (MIT)
+
+Copyright (c) 2014 Daniel Joos
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in all
+copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
+SOFTWARE. \ No newline at end of file
diff --git a/vendor/github.com/danieljoos/wincred/README.md b/vendor/github.com/danieljoos/wincred/README.md
new file mode 100644
index 0000000..8a879b0
--- /dev/null
+++ b/vendor/github.com/danieljoos/wincred/README.md
@@ -0,0 +1,145 @@
+wincred
+=======
+
+Go wrapper around the Windows Credential Manager API functions.
+
+[![GitHub release](https://img.shields.io/github/release/danieljoos/wincred.svg?style=flat-square)](https://github.com/danieljoos/wincred/releases/latest)
+[![Test Status](https://img.shields.io/github/actions/workflow/status/danieljoos/wincred/test.yml?label=test&logo=github&style=flat-square)](https://github.com/danieljoos/wincred/actions?query=workflow%3Atest)
+[![Go Report Card](https://goreportcard.com/badge/github.com/danieljoos/wincred)](https://goreportcard.com/report/github.com/danieljoos/wincred)
+[![Codecov](https://img.shields.io/codecov/c/github/danieljoos/wincred?logo=codecov&style=flat-square)](https://codecov.io/gh/danieljoos/wincred)
+[![PkgGoDev](https://img.shields.io/badge/go.dev-docs-007d9c?logo=go&logoColor=white&style=flat-square)](https://pkg.go.dev/github.com/danieljoos/wincred)
+
+Installation
+------------
+
+```Go
+go get github.com/danieljoos/wincred
+```
+
+
+Usage
+-----
+
+See the following examples:
+
+### Create and store a new generic credential object
+```Go
+package main
+
+import (
+ "fmt"
+ "github.com/danieljoos/wincred"
+)
+
+func main() {
+ cred := wincred.NewGenericCredential("myGoApplication")
+ cred.CredentialBlob = []byte("my secret")
+ err := cred.Write()
+
+ if err != nil {
+ fmt.Println(err)
+ }
+}
+```
+
+### Retrieve a credential object
+```Go
+package main
+
+import (
+ "fmt"
+ "github.com/danieljoos/wincred"
+)
+
+func main() {
+ cred, err := wincred.GetGenericCredential("myGoApplication")
+ if err == nil {
+ fmt.Println(string(cred.CredentialBlob))
+ }
+}
+```
+
+### Remove a credential object
+```Go
+package main
+
+import (
+ "fmt"
+ "github.com/danieljoos/wincred"
+)
+
+func main() {
+ cred, err := wincred.GetGenericCredential("myGoApplication")
+ if err != nil {
+ fmt.Println(err)
+ return
+ }
+ cred.Delete()
+}
+```
+
+### List all available credentials
+```Go
+package main
+
+import (
+ "fmt"
+ "github.com/danieljoos/wincred"
+)
+
+func main() {
+ creds, err := wincred.List()
+ if err != nil {
+ fmt.Println(err)
+ return
+ }
+ for i := range(creds) {
+ fmt.Println(creds[i].TargetName)
+ }
+}
+```
+
+Hints
+-----
+
+### Encoding
+
+The credential objects simply store byte arrays without specific meaning or encoding.
+For sharing between different applications, it might make sense to apply an explicit string encoding - for example **UTF-16 LE** (used nearly everywhere in the Win32 API).
+
+```Go
+package main
+
+import (
+ "fmt"
+ "os"
+
+ "github.com/danieljoos/wincred"
+ "golang.org/x/text/encoding/unicode"
+ "golang.org/x/text/transform"
+)
+
+func main() {
+ cred := wincred.NewGenericCredential("myGoApplication")
+
+ encoder := unicode.UTF16(unicode.LittleEndian, unicode.IgnoreBOM).NewEncoder()
+ blob, _, err := transform.Bytes(encoder, []byte("mysecret"))
+ if err != nil {
+ fmt.Println(err)
+ os.Exit(1)
+ }
+
+ cred.CredentialBlob = blob
+ err = cred.Write()
+
+ if err != nil {
+ fmt.Println(err)
+ os.Exit(1)
+ }
+}
+
+```
+
+### Limitations
+
+The size of a credential blob is limited to **2560 Bytes** by the Windows API.
diff --git a/vendor/github.com/danieljoos/wincred/conversion.go b/vendor/github.com/danieljoos/wincred/conversion.go
new file mode 100644
index 0000000..bc04f50
--- /dev/null
+++ b/vendor/github.com/danieljoos/wincred/conversion.go
@@ -0,0 +1,116 @@
+// +build windows
+
+package wincred
+
+import (
+ "encoding/binary"
+ "reflect"
+ "time"
+ "unsafe"
+
+ syscall "golang.org/x/sys/windows"
+)
+
+// utf16ToByte creates a byte array from a given UTF 16 char array.
+func utf16ToByte(wstr []uint16) (result []byte) {
+ result = make([]byte, len(wstr)*2)
+ for i := range wstr {
+ binary.LittleEndian.PutUint16(result[(i*2):(i*2)+2], wstr[i])
+ }
+ return
+}
+
+// utf16FromString creates a UTF16 char array from a string.
+func utf16FromString(str string) []uint16 {
+ res, err := syscall.UTF16FromString(str)
+ if err != nil {
+ return []uint16{}
+ }
+ return res
+}
+
+// goBytes copies the given C byte array to a Go byte array (see `C.GoBytes`).
+// This function avoids having cgo as dependency.
+func goBytes(src uintptr, len uint32) []byte {
+ if src == uintptr(0) {
+ return []byte{}
+ }
+ rv := make([]byte, len)
+ copy(rv, *(*[]byte)(unsafe.Pointer(&reflect.SliceHeader{
+ Data: src,
+ Len: int(len),
+ Cap: int(len),
+ })))
+ return rv
+}
+
+// Convert the given CREDENTIAL struct to a more usable structure
+func sysToCredential(cred *sysCREDENTIAL) (result *Credential) {
+ if cred == nil {
+ return nil
+ }
+ result = new(Credential)
+ result.Comment = syscall.UTF16PtrToString(cred.Comment)
+ result.TargetName = syscall.UTF16PtrToString(cred.TargetName)
+ result.TargetAlias = syscall.UTF16PtrToString(cred.TargetAlias)
+ result.UserName = syscall.UTF16PtrToString(cred.UserName)
+ result.LastWritten = time.Unix(0, cred.LastWritten.Nanoseconds())
+ result.Persist = CredentialPersistence(cred.Persist)
+ result.CredentialBlob = goBytes(cred.CredentialBlob, cred.CredentialBlobSize)
+ result.Attributes = make([]CredentialAttribute, cred.AttributeCount)
+ attrSlice := *(*[]sysCREDENTIAL_ATTRIBUTE)(unsafe.Pointer(&reflect.SliceHeader{
+ Data: cred.Attributes,
+ Len: int(cred.AttributeCount),
+ Cap: int(cred.AttributeCount),
+ }))
+ for i, attr := range attrSlice {
+ resultAttr := &result.Attributes[i]
+ resultAttr.Keyword = syscall.UTF16PtrToString(attr.Keyword)
+ resultAttr.Value = goBytes(attr.Value, attr.ValueSize)
+ }
+ return result
+}
+
+// Convert the given Credential object back to a CREDENTIAL struct, which can be used for calling the
+// Windows APIs
+func sysFromCredential(cred *Credential) (result *sysCREDENTIAL) {
+ if cred == nil {
+ return nil
+ }
+ result = new(sysCREDENTIAL)
+ result.Flags = 0
+ result.Type = 0
+ result.TargetName, _ = syscall.UTF16PtrFromString(cred.TargetName)
+ result.Comment, _ = syscall.UTF16PtrFromString(cred.Comment)
+ result.LastWritten = syscall.NsecToFiletime(cred.LastWritten.UnixNano())
+ result.CredentialBlobSize = uint32(len(cred.CredentialBlob))
+ if len(cred.CredentialBlob) > 0 {
+ result.CredentialBlob = uintptr(unsafe.Pointer(&cred.CredentialBlob[0]))
+ } else {
+ result.CredentialBlob = 0
+ }
+ result.Persist = uint32(cred.Persist)
+ result.AttributeCount = uint32(len(cred.Attributes))
+ attributes := make([]sysCREDENTIAL_ATTRIBUTE, len(cred.Attributes))
+ if len(attributes) > 0 {
+ result.Attributes = uintptr(unsafe.Pointer(&attributes[0]))
+ } else {
+ result.Attributes = 0
+ }
+ for i := range cred.Attributes {
+ inAttr := &cred.Attributes[i]
+ outAttr := &attributes[i]
+ outAttr.Keyword, _ = syscall.UTF16PtrFromString(inAttr.Keyword)
+ outAttr.Flags = 0
+ outAttr.ValueSize = uint32(len(inAttr.Value))
+ if len(inAttr.Value) > 0 {
+ outAttr.Value = uintptr(unsafe.Pointer(&inAttr.Value[0]))
+ } else {
+ outAttr.Value = 0
+ }
+ }
+ result.TargetAlias, _ = syscall.UTF16PtrFromString(cred.TargetAlias)
+ result.UserName, _ = syscall.UTF16PtrFromString(cred.UserName)
+
+ return
+}
diff --git a/vendor/github.com/danieljoos/wincred/conversion_unsupported.go b/vendor/github.com/danieljoos/wincred/conversion_unsupported.go
new file mode 100644
index 0000000..a1ea720
--- /dev/null
+++ b/vendor/github.com/danieljoos/wincred/conversion_unsupported.go
@@ -0,0 +1,11 @@
+// +build !windows
+
+package wincred
+
+func utf16ToByte(...interface{}) []byte {
+ return nil
+}
+
+func utf16FromString(...interface{}) []uint16 {
+ return nil
+}
diff --git a/vendor/github.com/danieljoos/wincred/sys.go b/vendor/github.com/danieljoos/wincred/sys.go
new file mode 100644
index 0000000..fb8a6ac
--- /dev/null
+++ b/vendor/github.com/danieljoos/wincred/sys.go
@@ -0,0 +1,148 @@
+//go:build windows
+// +build windows
+
+package wincred
+
+import (
+ "reflect"
+ "syscall"
+ "unsafe"
+
+ "golang.org/x/sys/windows"
+)
+
+var (
+ modadvapi32 = windows.NewLazySystemDLL("advapi32.dll")
+ procCredRead = modadvapi32.NewProc("CredReadW")
+ procCredWrite proc = modadvapi32.NewProc("CredWriteW")
+ procCredDelete proc = modadvapi32.NewProc("CredDeleteW")
+ procCredFree proc = modadvapi32.NewProc("CredFree")
+ procCredEnumerate = modadvapi32.NewProc("CredEnumerateW")
+)
+
+// Interface for syscall.Proc: helps testing
+type proc interface {
+ Call(a ...uintptr) (r1, r2 uintptr, lastErr error)
+}
+
+// https://docs.microsoft.com/en-us/windows/desktop/api/wincred/ns-wincred-_credentialw
+type sysCREDENTIAL struct {
+ Flags uint32
+ Type uint32
+ TargetName *uint16
+ Comment *uint16
+ LastWritten windows.Filetime
+ CredentialBlobSize uint32
+ CredentialBlob uintptr
+ Persist uint32
+ AttributeCount uint32
+ Attributes uintptr
+ TargetAlias *uint16
+ UserName *uint16
+}
+
+// https://docs.microsoft.com/en-us/windows/desktop/api/wincred/ns-wincred-_credential_attributew
+type sysCREDENTIAL_ATTRIBUTE struct {
+ Keyword *uint16
+ Flags uint32
+ ValueSize uint32
+ Value uintptr
+}
+
+// https://docs.microsoft.com/en-us/windows/desktop/api/wincred/ns-wincred-_credentialw
+type sysCRED_TYPE uint32
+
+const (
+ sysCRED_TYPE_GENERIC sysCRED_TYPE = 0x1
+ sysCRED_TYPE_DOMAIN_PASSWORD sysCRED_TYPE = 0x2
+ sysCRED_TYPE_DOMAIN_CERTIFICATE sysCRED_TYPE = 0x3
+ sysCRED_TYPE_DOMAIN_VISIBLE_PASSWORD sysCRED_TYPE = 0x4
+ sysCRED_TYPE_GENERIC_CERTIFICATE sysCRED_TYPE = 0x5
+ sysCRED_TYPE_DOMAIN_EXTENDED sysCRED_TYPE = 0x6
+
+ // https://docs.microsoft.com/en-us/windows/desktop/Debug/system-error-codes
+ sysERROR_NOT_FOUND = windows.Errno(1168)
+ sysERROR_INVALID_PARAMETER = windows.Errno(87)
+ sysERROR_BAD_USERNAME = windows.Errno(2202)
+)
+
+// https://docs.microsoft.com/en-us/windows/desktop/api/wincred/nf-wincred-credreadw
+func sysCredRead(targetName string, typ sysCRED_TYPE) (*Credential, error) {
+ var pcred *sysCREDENTIAL
+ targetNamePtr, _ := windows.UTF16PtrFromString(targetName)
+ ret, _, err := syscall.SyscallN(
+ procCredRead.Addr(),
+ uintptr(unsafe.Pointer(targetNamePtr)),
+ uintptr(typ),
+ 0,
+ uintptr(unsafe.Pointer(&pcred)),
+ )
+ if ret == 0 {
+ return nil, err
+ }
+ defer procCredFree.Call(uintptr(unsafe.Pointer(pcred)))
+
+ return sysToCredential(pcred), nil
+}
+
+// https://docs.microsoft.com/en-us/windows/desktop/api/wincred/nf-wincred-credwritew
+func sysCredWrite(cred *Credential, typ sysCRED_TYPE) error {
+ ncred := sysFromCredential(cred)
+ ncred.Type = uint32(typ)
+ ret, _, err := procCredWrite.Call(
+ uintptr(unsafe.Pointer(ncred)),
+ 0,
+ )
+ if ret == 0 {
+ return err
+ }
+
+ return nil
+}
+
+// https://docs.microsoft.com/en-us/windows/desktop/api/wincred/nf-wincred-creddeletew
+func sysCredDelete(cred *Credential, typ sysCRED_TYPE) error {
+ targetNamePtr, _ := windows.UTF16PtrFromString(cred.TargetName)
+ ret, _, err := procCredDelete.Call(
+ uintptr(unsafe.Pointer(targetNamePtr)),
+ uintptr(typ),
+ 0,
+ )
+ if ret == 0 {
+ return err
+ }
+
+ return nil
+}
+
+// https://docs.microsoft.com/en-us/windows/desktop/api/wincred/nf-wincred-credenumeratew
+func sysCredEnumerate(filter string, all bool) ([]*Credential, error) {
+ var count int
+ var pcreds uintptr
+ var filterPtr *uint16
+ if !all {
+ filterPtr, _ = windows.UTF16PtrFromString(filter)
+ }
+ ret, _, err := syscall.SyscallN(
+ procCredEnumerate.Addr(),
+ uintptr(unsafe.Pointer(filterPtr)),
+ 0,
+ uintptr(unsafe.Pointer(&count)),
+ uintptr(unsafe.Pointer(&pcreds)),
+ )
+ if ret == 0 {
+ return nil, err
+ }
+ defer procCredFree.Call(pcreds)
+ credsSlice := *(*[]*sysCREDENTIAL)(unsafe.Pointer(&reflect.SliceHeader{
+ Data: pcreds,
+ Len: count,
+ Cap: count,
+ }))
+ creds := make([]*Credential, count, count)
+ for i, cred := range credsSlice {
+ creds[i] = sysToCredential(cred)
+ }
+
+ return creds, nil
+}
diff --git a/vendor/github.com/danieljoos/wincred/sys_unsupported.go b/vendor/github.com/danieljoos/wincred/sys_unsupported.go
new file mode 100644
index 0000000..b47bccf
--- /dev/null
+++ b/vendor/github.com/danieljoos/wincred/sys_unsupported.go
@@ -0,0 +1,36 @@
+// +build !windows
+
+package wincred
+
+import (
+ "errors"
+ "syscall"
+)
+
+const (
+ sysCRED_TYPE_GENERIC = 0
+ sysCRED_TYPE_DOMAIN_PASSWORD = 0
+ sysCRED_TYPE_DOMAIN_CERTIFICATE = 0
+ sysCRED_TYPE_DOMAIN_VISIBLE_PASSWORD = 0
+ sysCRED_TYPE_GENERIC_CERTIFICATE = 0
+ sysCRED_TYPE_DOMAIN_EXTENDED = 0
+
+ sysERROR_NOT_FOUND = syscall.Errno(1)
+ sysERROR_INVALID_PARAMETER = syscall.Errno(1)
+)
+
+func sysCredRead(...interface{}) (*Credential, error) {
+ return nil, errors.New("Operation not supported")
+}
+
+func sysCredWrite(...interface{}) error {
+ return errors.New("Operation not supported")
+}
+
+func sysCredDelete(...interface{}) error {
+ return errors.New("Operation not supported")
+}
+
+func sysCredEnumerate(...interface{}) ([]*Credential, error) {
+ return nil, errors.New("Operation not supported")
+}
diff --git a/vendor/github.com/danieljoos/wincred/types.go b/vendor/github.com/danieljoos/wincred/types.go
new file mode 100644
index 0000000..28debc9
--- /dev/null
+++ b/vendor/github.com/danieljoos/wincred/types.go
@@ -0,0 +1,69 @@
+package wincred
+
+import (
+ "time"
+)
+
+// CredentialPersistence describes one of three persistence modes of a credential.
+// A detailed description of the available modes can be found on
+// Docs: https://docs.microsoft.com/en-us/windows/desktop/api/wincred/ns-wincred-_credentialw
+type CredentialPersistence uint32
+
+const (
+ // PersistSession indicates that the credential only persists for the life
+ // of the current Windows login session. Such a credential is not visible in
+ // any other logon session, even from the same user.
+ PersistSession CredentialPersistence = 0x1
+
+ // PersistLocalMachine indicates that the credential persists for this and
+ // all subsequent logon sessions on this local machine/computer. It is
+ // however not visible for logon sessions of this user on a different
+ // machine.
+ PersistLocalMachine CredentialPersistence = 0x2
+
+ // PersistEnterprise indicates that the credential persists for this and all
+ // subsequent logon sessions for this user. It is also visible for logon
+ // sessions on different computers.
+ PersistEnterprise CredentialPersistence = 0x3
+)
+
+// CredentialAttribute represents an application-specific attribute of a credential.
+type CredentialAttribute struct {
+ Keyword string
+ Value []byte
+}
+
+// Credential is the basic credential structure.
+// A credential is identified by its target name.
+// The actual credential secret is available in the CredentialBlob field.
+type Credential struct {
+ TargetName string
+ Comment string
+ LastWritten time.Time
+ CredentialBlob []byte
+ Attributes []CredentialAttribute
+ TargetAlias string
+ UserName string
+ Persist CredentialPersistence
+}
+
+// GenericCredential holds a credential for generic usage.
+// It is typically defined and used by applications that need to manage user
+// secrets.
+//
+// More information about the available kinds of credentials of the Windows
+// Credential Management API can be found on Docs:
+// https://docs.microsoft.com/en-us/windows/desktop/SecAuthN/kinds-of-credentials
+type GenericCredential struct {
+ Credential
+}
+
+// DomainPassword holds a domain credential that is typically used by the
+// operating system for user logon.
+//
+// More information about the available kinds of credentials of the Windows
+// Credential Management API can be found on Docs:
+// https://docs.microsoft.com/en-us/windows/desktop/SecAuthN/kinds-of-credentials
+type DomainPassword struct {
+ Credential
+}
diff --git a/vendor/github.com/danieljoos/wincred/wincred.go b/vendor/github.com/danieljoos/wincred/wincred.go
new file mode 100644
index 0000000..5632ee9
--- /dev/null
+++ b/vendor/github.com/danieljoos/wincred/wincred.go
@@ -0,0 +1,114 @@
+// Package wincred provides primitives for accessing the Windows Credentials Management API.
+// This includes functions for retrieval, listing and storage of credentials as well as Go structures for convenient access to the credential data.
+//
+// A more detailed description of Windows Credentials Management can be found on
+// Docs: https://docs.microsoft.com/en-us/windows/desktop/SecAuthN/credentials-management
+package wincred
+
+import "errors"
+
+const (
+ // ErrElementNotFound is the error that is returned if a requested element cannot be found.
+ // This error constant can be used to check if a credential could not be found.
+ ErrElementNotFound = sysERROR_NOT_FOUND
+
+ // ErrInvalidParameter is the error that is returned for invalid parameters.
+ // This error constant can be used to check if the given function parameters were invalid.
+ // For example when trying to create a new generic credential with an empty target name.
+ ErrInvalidParameter = sysERROR_INVALID_PARAMETER
+
+ // ErrBadUsername is returned when the credential's username is invalid.
+ ErrBadUsername = sysERROR_BAD_USERNAME
+)
+
+// GetGenericCredential fetches the generic credential with the given name from Windows credential manager.
+// It returns nil and an error if the credential could not be found or an error occurred.
+func GetGenericCredential(targetName string) (*GenericCredential, error) {
+ cred, err := sysCredRead(targetName, sysCRED_TYPE_GENERIC)
+ if cred != nil {
+ return &GenericCredential{Credential: *cred}, err
+ }
+ return nil, err
+}
+
+// NewGenericCredential creates a new generic credential object with the given name.
+// The persist mode of the newly created object is set to a default value that indicates local-machine-wide storage.
+// The credential object is NOT yet persisted to the Windows credential vault.
+func NewGenericCredential(targetName string) (result *GenericCredential) {
+ result = new(GenericCredential)
+ result.TargetName = targetName
+ result.Persist = PersistLocalMachine
+ return
+}
+
+// Write persists the generic credential object to Windows credential manager.
+func (t *GenericCredential) Write() (err error) {
+ err = sysCredWrite(&t.Credential, sysCRED_TYPE_GENERIC)
+ return
+}
+
+// Delete removes the credential object from Windows credential manager.
+func (t *GenericCredential) Delete() (err error) {
+ err = sysCredDelete(&t.Credential, sysCRED_TYPE_GENERIC)
+ return
+}
+
+// GetDomainPassword fetches the domain-password credential with the given target host name from Windows credential manager.
+// It returns nil and an error if the credential could not be found or an error occurred.
+func GetDomainPassword(targetName string) (*DomainPassword, error) {
+ cred, err := sysCredRead(targetName, sysCRED_TYPE_DOMAIN_PASSWORD)
+ if cred != nil {
+ return &DomainPassword{Credential: *cred}, err
+ }
+ return nil, err
+}
+
+// NewDomainPassword creates a new domain-password credential used for login to the given target host name.
+// The persist mode of the newly created object is set to a default value that indicates local-machine-wide storage.
+// The credential object is NOT yet persisted to the Windows credential vault.
+func NewDomainPassword(targetName string) (result *DomainPassword) {
+ result = new(DomainPassword)
+ result.TargetName = targetName
+ result.Persist = PersistLocalMachine
+ return
+}
+
+// Write persists the domain-password credential to Windows credential manager.
+func (t *DomainPassword) Write() (err error) {
+ err = sysCredWrite(&t.Credential, sysCRED_TYPE_DOMAIN_PASSWORD)
+ return
+}
+
+// Delete removes the domain-password credential from Windows credential manager.
+func (t *DomainPassword) Delete() (err error) {
+ err = sysCredDelete(&t.Credential, sysCRED_TYPE_DOMAIN_PASSWORD)
+ return
+}
+
+// SetPassword sets the CredentialBlob field of a domain password credential to the given string.
+func (t *DomainPassword) SetPassword(pw string) {
+ t.CredentialBlob = utf16ToByte(utf16FromString(pw))
+}
+
+// List retrieves all credentials of the Credentials store.
+func List() ([]*Credential, error) {
+ creds, err := sysCredEnumerate("", true)
+ if err != nil && errors.Is(err, ErrElementNotFound) {
+ // Ignore ERROR_NOT_FOUND and return an empty list instead
+ creds = []*Credential{}
+ err = nil
+ }
+ return creds, err
+}
+
+// FilteredList retrieves the list of credentials from the Credentials store that match the given filter.
+// The filter string defines the prefix followed by an asterisk for the `TargetName` attribute of the credentials.
+func FilteredList(filter string) ([]*Credential, error) {
+ creds, err := sysCredEnumerate(filter, false)
+ if err != nil && errors.Is(err, ErrElementNotFound) {
+ // Ignore ERROR_NOT_FOUND and return an empty list instead
+ creds = []*Credential{}
+ err = nil
+ }
+ return creds, err
+}