Skip to content
GitLab
Projects
Groups
Snippets
/
Help
Help
Support
Community forum
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in
Toggle navigation
Menu
Open sidebar
IRMA
Github mirrors
irmago
Commits
ea159ad6
Commit
ea159ad6
authored
Oct 03, 2017
by
Sietse Ringers
Browse files
Separating storage methods from CredentialManager
parent
9c527942
Changes
5
Hide whitespace changes
Inline
Side-by-side
configstore.go
View file @
ea159ad6
...
...
@@ -27,22 +27,38 @@ type ConfigurationStore struct {
// NewConfigurationStore returns a new configuration store. After this
// ParseFolder() should be called to parse the specified path.
func
NewConfigurationStore
(
path
string
)
(
store
*
ConfigurationStore
)
{
func
NewConfigurationStore
(
path
string
,
assets
string
)
(
store
*
ConfigurationStore
,
err
error
)
{
store
=
&
ConfigurationStore
{
SchemeManagers
:
make
(
map
[
SchemeManagerIdentifier
]
*
SchemeManager
),
Issuers
:
make
(
map
[
IssuerIdentifier
]
*
Issuer
),
Credentials
:
make
(
map
[
CredentialTypeIdentifier
]
*
CredentialType
),
publicKeys
:
make
(
map
[
IssuerIdentifier
][]
*
gabi
.
PublicKey
),
reverseHashes
:
make
(
map
[
string
]
CredentialTypeIdentifier
),
path
:
path
,
path
:
path
,
}
var
exist
bool
if
exist
,
err
=
PathExists
(
store
.
path
);
err
!=
nil
{
return
nil
,
err
}
if
!
exist
{
if
err
=
ensureDirectoryExists
(
store
.
path
);
err
!=
nil
{
return
nil
,
err
}
if
assets
!=
""
{
if
err
=
store
.
Copy
(
assets
,
false
);
err
!=
nil
{
return
nil
,
err
}
}
}
return
}
// ParseFolder populates the current store by parsing the storage path,
// listing the containing scheme managers, issuers and credential types.
func
(
store
*
ConfigurationStore
)
ParseFolder
()
error
{
*
store
=
*
NewConfigurationStore
(
store
.
path
)
// Init all maps
// Init all maps
store
.
SchemeManagers
=
make
(
map
[
SchemeManagerIdentifier
]
*
SchemeManager
)
store
.
Issuers
=
make
(
map
[
IssuerIdentifier
]
*
Issuer
)
store
.
Credentials
=
make
(
map
[
CredentialTypeIdentifier
]
*
CredentialType
)
store
.
publicKeys
=
make
(
map
[
IssuerIdentifier
][]
*
gabi
.
PublicKey
)
store
.
reverseHashes
=
make
(
map
[
string
]
CredentialTypeIdentifier
)
err
:=
iterateSubfolders
(
store
.
path
,
func
(
dir
string
)
error
{
manager
:=
&
SchemeManager
{}
...
...
irmago_test.go
View file @
ea159ad6
...
...
@@ -227,7 +227,8 @@ func TestMetadataAttribute(t *testing.T) {
}
func
TestMetadataCompatibility
(
t
*
testing
.
T
)
{
store
:=
NewConfigurationStore
(
"testdata/irma_configuration"
)
store
,
err
:=
NewConfigurationStore
(
"testdata/irma_configuration"
,
""
)
require
.
NoError
(
t
,
err
)
require
.
NoError
(
t
,
store
.
ParseFolder
())
// An actual metadata attribute of an IRMA credential extracted from the IRMA app
...
...
@@ -248,8 +249,9 @@ func TestMetadataCompatibility(t *testing.T) {
}
func
TestAttributeDisjunctionMarshaling
(
t
*
testing
.
T
)
{
store
:=
NewConfigurationStore
(
"testdata/irma_configuration"
)
store
.
ParseFolder
()
store
,
err
:=
NewConfigurationStore
(
"testdata/irma_configuration"
,
""
)
require
.
NoError
(
t
,
err
)
require
.
NoError
(
t
,
store
.
ParseFolder
())
disjunction
:=
AttributeDisjunction
{}
var
_
json
.
Unmarshaler
=
&
disjunction
...
...
manager.go
View file @
ea159ad6
...
...
@@ -15,13 +15,13 @@ import (
// CredentialManager manages credentials.
type
CredentialManager
struct
{
secretkey
*
secretKey
storagePath
string
attributes
map
[
CredentialTypeIdentifier
][]
*
AttributeList
credentials
map
[
CredentialTypeIdentifier
]
map
[
int
]
*
credential
keyshareServers
map
[
SchemeManagerIdentifier
]
*
keyshareServer
paillierKeyCache
*
paillierPrivateKey
logs
[]
*
LogEntry
storage
storage
irmaConfigurationPath
string
androidStoragePath
string
ConfigurationStore
*
ConfigurationStore
...
...
@@ -32,6 +32,91 @@ type secretKey struct {
Key
*
big
.
Int
}
// NewCredentialManager creates a new CredentialManager that uses the directory
// specified by storagePath for (de)serializing itself. irmaConfigurationPath
// is the path to a (possibly readonly) folder containing irma_configuration;
// androidStoragePath is an optional path to the files of the old android app
// (specify "" if you do not want to parse the old android app files),
// and keyshareHandler is used for when a registration to a keyshare server needs
// to happen.
// The credential manager returned by this function has been fully deserialized
// and is ready for use.
//
// NOTE: It is the responsibility of the caller that there exists a directory
// at storagePath!
func
NewCredentialManager
(
storagePath
string
,
irmaConfigurationPath
string
,
androidStoragePath
string
,
keyshareHandler
KeyshareHandler
,
)
(
*
CredentialManager
,
error
)
{
var
err
error
if
err
=
AssertPathExists
(
storagePath
);
err
!=
nil
{
return
nil
,
err
}
if
err
=
AssertPathExists
(
irmaConfigurationPath
);
err
!=
nil
{
return
nil
,
err
}
var
store
*
ConfigurationStore
if
store
,
err
=
NewConfigurationStore
(
storagePath
+
"/irma_configuration"
,
irmaConfigurationPath
);
err
!=
nil
{
return
nil
,
err
}
if
err
=
store
.
ParseFolder
();
err
!=
nil
{
return
nil
,
err
}
cm
:=
&
CredentialManager
{
credentials
:
make
(
map
[
CredentialTypeIdentifier
]
map
[
int
]
*
credential
),
keyshareServers
:
make
(
map
[
SchemeManagerIdentifier
]
*
keyshareServer
),
attributes
:
make
(
map
[
CredentialTypeIdentifier
][]
*
AttributeList
),
irmaConfigurationPath
:
irmaConfigurationPath
,
androidStoragePath
:
androidStoragePath
,
ConfigurationStore
:
store
,
storage
:
storage
{
storagePath
:
storagePath
,
ConfigurationStore
:
store
},
}
// Ensure storage path exists, and populate it with necessary files
if
err
=
cm
.
storage
.
ensureStorageExists
();
err
!=
nil
{
return
nil
,
err
}
// Perform new update functions from credentialManagerUpdates, if any
if
err
=
cm
.
update
();
err
!=
nil
{
return
nil
,
err
}
// Load our stuff
if
cm
.
secretkey
,
err
=
cm
.
storage
.
loadSecretKey
();
err
!=
nil
{
return
nil
,
err
}
if
cm
.
attributes
,
err
=
cm
.
storage
.
loadAttributes
();
err
!=
nil
{
return
nil
,
err
}
if
cm
.
paillierKeyCache
,
err
=
cm
.
storage
.
loadPaillierKeys
();
err
!=
nil
{
return
nil
,
err
}
if
cm
.
keyshareServers
,
err
=
cm
.
storage
.
loadKeyshareServers
();
err
!=
nil
{
return
nil
,
err
}
unenrolled
:=
cm
.
unenrolledKeyshareServers
()
switch
len
(
unenrolled
)
{
case
0
:
// nop
case
1
:
if
keyshareHandler
==
nil
{
return
nil
,
errors
.
New
(
"Keyshare server found but no KeyshareHandler was given"
)
}
keyshareHandler
.
StartRegistration
(
unenrolled
[
0
],
func
(
email
,
pin
string
)
{
cm
.
KeyshareEnroll
(
unenrolled
[
0
]
.
Identifier
(),
email
,
pin
)
})
default
:
return
nil
,
errors
.
New
(
"Too many keyshare servers"
)
}
return
cm
,
nil
}
// CredentialInfoList returns a list of information of all contained credentials.
func
(
cm
*
CredentialManager
)
CredentialInfoList
()
CredentialInfoList
{
list
:=
CredentialInfoList
([]
*
CredentialInfo
{})
...
...
@@ -57,7 +142,7 @@ func (cm *CredentialManager) remove(id CredentialTypeIdentifier, index int, stor
attrs
:=
list
[
index
]
cm
.
attributes
[
id
]
=
append
(
list
[
:
index
],
list
[
index
+
1
:
]
...
)
if
storenow
{
cm
.
storeAttributes
()
cm
.
storage
.
storeAttributes
(
cm
.
attributes
)
}
// Remove credential
...
...
@@ -69,7 +154,7 @@ func (cm *CredentialManager) remove(id CredentialTypeIdentifier, index int, stor
}
// Remove signature from storage
if
err
:=
os
.
Remove
(
cm
.
signatureFilename
(
attrs
));
err
!=
nil
{
if
err
:=
os
.
Remove
(
cm
.
storage
.
signatureFilename
(
attrs
));
err
!=
nil
{
return
err
}
...
...
@@ -99,18 +184,10 @@ func (cm *CredentialManager) RemoveAllCredentials() error {
return
err
}
}
if
err
:=
cm
.
storeAttributes
();
err
!=
nil
{
if
err
:=
cm
.
storage
.
storeAttributes
(
cm
.
attributes
);
err
!=
nil
{
return
err
}
return
cm
.
storeLogs
()
}
func
(
cm
*
CredentialManager
)
generateSecretKey
()
(
*
secretKey
,
error
)
{
key
,
err
:=
gabi
.
RandomBigInt
(
gabi
.
DefaultSystemParameters
[
1024
]
.
Lm
)
if
err
!=
nil
{
return
nil
,
err
}
return
&
secretKey
{
Key
:
key
},
nil
return
cm
.
storage
.
storeLogs
(
cm
.
logs
)
}
// attrs returns cm.attributes[id], initializing it to an empty slice if neccesary
...
...
@@ -168,7 +245,7 @@ func (cm *CredentialManager) credential(id CredentialTypeIdentifier, counter int
if
attrs
==
nil
{
// We do not have the requested cred
return
}
sig
,
err
:=
cm
.
loadSignature
(
attrs
)
sig
,
err
:=
cm
.
storage
.
loadSignature
(
attrs
)
if
err
!=
nil
{
return
nil
,
err
}
...
...
@@ -209,11 +286,11 @@ func (cm *CredentialManager) addCredential(cred *credential, storeAttributes boo
counter
:=
len
(
cm
.
attributes
[
id
])
-
1
cm
.
credentials
[
id
][
counter
]
=
cred
if
err
=
cm
.
storeSignature
(
cred
,
counter
);
err
!=
nil
{
if
err
=
cm
.
storage
.
storeSignature
(
cred
);
err
!=
nil
{
return
}
if
storeAttributes
{
err
=
cm
.
storeAttributes
()
err
=
cm
.
storage
.
storeAttributes
(
cm
.
attributes
)
}
return
}
...
...
@@ -473,7 +550,7 @@ func (cm *CredentialManager) KeyshareEnroll(managerID SchemeManagerIdentifier, e
}
cm
.
keyshareServers
[
managerID
]
=
kss
return
cm
.
storeKeyshareServers
()
return
cm
.
storage
.
storeKeyshareServers
(
cm
.
keyshareServers
)
}
// KeyshareRemove unregisters the keyshare server of the specified scheme manager.
...
...
@@ -482,13 +559,13 @@ func (cm *CredentialManager) KeyshareRemove(manager SchemeManagerIdentifier) err
return
errors
.
New
(
"Can't uninstall unknown keyshare server"
)
}
delete
(
cm
.
keyshareServers
,
manager
)
return
cm
.
storeKeyshareServers
()
return
cm
.
storage
.
storeKeyshareServers
(
cm
.
keyshareServers
)
}
func
(
cm
*
CredentialManager
)
addLogEntry
(
entry
*
LogEntry
,
storenow
bool
)
error
{
cm
.
logs
=
append
(
cm
.
logs
,
entry
)
if
storenow
{
return
cm
.
stor
eLogs
(
)
return
cm
.
stor
age
.
storeLogs
(
cm
.
logs
)
}
return
nil
}
...
...
@@ -496,7 +573,7 @@ func (cm *CredentialManager) addLogEntry(entry *LogEntry, storenow bool) error {
func
(
cm
*
CredentialManager
)
Logs
()
([]
*
LogEntry
,
error
)
{
if
cm
.
logs
==
nil
||
len
(
cm
.
logs
)
==
0
{
var
err
error
cm
.
logs
,
err
=
cm
.
loadLogs
()
cm
.
logs
,
err
=
cm
.
storage
.
loadLogs
()
if
err
!=
nil
{
return
nil
,
err
}
...
...
storage.go
View file @
ea159ad6
...
...
@@ -7,12 +7,17 @@ import (
"io/ioutil"
"os"
"path"
"time"
"github.com/go-errors/errors"
"github.com/mhe/gabi"
)
// Storage provider for a CredentialManager
type
storage
struct
{
storagePath
string
ConfigurationStore
*
ConfigurationStore
}
// Filenames in which we store stuff
const
(
skFile
=
"sk"
...
...
@@ -24,6 +29,19 @@ const (
signaturesDir
=
"sigs"
)
// AssertPathExists returns nil only if it has been successfully
// verified that the specified path exists.
func
AssertPathExists
(
path
string
)
error
{
exist
,
err
:=
PathExists
(
path
)
if
err
!=
nil
{
return
err
}
if
!
exist
{
return
errors
.
Errorf
(
"Path %s does not exist"
,
path
)
}
return
nil
}
// PathExists checks if the specified path exists.
func
PathExists
(
path
string
)
(
bool
,
error
)
{
_
,
err
:=
os
.
Stat
(
path
)
...
...
@@ -71,146 +89,25 @@ func saveFile(filepath string, content []byte) (err error) {
return
os
.
Rename
(
dir
+
"/"
+
tempfilename
,
filepath
)
}
// NewCredentialManager creates a new CredentialManager that uses the directory
// specified by storagePath for (de)serializing itself. irmaConfigurationPath
// is the path to a (possibly readonly) folder containing irma_configuration;
// androidStoragePath is an optional path to the files of the old android app
// (specify "" if you do not want to parse the old android app files),
// and keyshareHandler is used for when a registration to a keyshare server needs
// to happen.
// The credential manager returned by this function has been fully deserialized
// and is ready for use.
//
// NOTE: It is the responsibility of the caller that there exists a directory
// at storagePath!
func
NewCredentialManager
(
storagePath
string
,
irmaConfigurationPath
string
,
androidStoragePath
string
,
keyshareHandler
KeyshareHandler
,
)
(
*
CredentialManager
,
error
)
{
var
err
error
cm
:=
&
CredentialManager
{
credentials
:
make
(
map
[
CredentialTypeIdentifier
]
map
[
int
]
*
credential
),
keyshareServers
:
make
(
map
[
SchemeManagerIdentifier
]
*
keyshareServer
),
attributes
:
make
(
map
[
CredentialTypeIdentifier
][]
*
AttributeList
),
irmaConfigurationPath
:
irmaConfigurationPath
,
androidStoragePath
:
androidStoragePath
,
ConfigurationStore
:
NewConfigurationStore
(
storagePath
+
"/irma_configuration"
),
}
exists
,
err
:=
PathExists
(
cm
.
irmaConfigurationPath
)
func
generateSecretKey
()
(
*
secretKey
,
error
)
{
key
,
err
:=
gabi
.
RandomBigInt
(
gabi
.
DefaultSystemParameters
[
1024
]
.
Lm
)
if
err
!=
nil
{
return
nil
,
err
}
if
!
exists
{
return
nil
,
errors
.
New
(
"irmaConfigurationPath does not exist"
)
}
// Ensure storage path exists, and populate it with necessary files
cm
.
storagePath
=
storagePath
if
err
=
cm
.
ensureStorageExists
();
err
!=
nil
{
return
nil
,
err
}
if
err
=
cm
.
ConfigurationStore
.
ParseFolder
();
err
!=
nil
{
return
nil
,
err
}
// Perform new update functions from credentialManagerUpdates, if any
if
err
=
cm
.
update
();
err
!=
nil
{
return
nil
,
err
}
// Load our stuff
if
cm
.
secretkey
,
err
=
cm
.
loadSecretKey
();
err
!=
nil
{
return
nil
,
err
}
if
cm
.
attributes
,
err
=
cm
.
loadAttributes
();
err
!=
nil
{
return
nil
,
err
}
if
cm
.
paillierKeyCache
,
err
=
cm
.
loadPaillierKeys
();
err
!=
nil
{
return
nil
,
err
}
if
cm
.
keyshareServers
,
err
=
cm
.
loadKeyshareServers
();
err
!=
nil
{
return
nil
,
err
}
unenrolled
:=
cm
.
unenrolledKeyshareServers
()
switch
len
(
unenrolled
)
{
case
0
:
// nop
case
1
:
if
keyshareHandler
==
nil
{
return
nil
,
errors
.
New
(
"Keyshare server found but no KeyshareHandler was given"
)
}
keyshareHandler
.
StartRegistration
(
unenrolled
[
0
],
func
(
email
,
pin
string
)
{
cm
.
KeyshareEnroll
(
unenrolled
[
0
]
.
Identifier
(),
email
,
pin
)
})
default
:
return
nil
,
errors
.
New
(
"Too many keyshare servers"
)
}
return
cm
,
nil
return
&
secretKey
{
Key
:
key
},
nil
}
// update performs any function from credentialManagerUpdates that has not
// already been executed in the past, keeping track of previously executed updates
// in the file at updatesFile.
func
(
cm
*
CredentialManager
)
update
()
error
{
// Load and parse file containing info about already performed updates
var
err
error
exists
,
err
:=
PathExists
(
cm
.
path
(
updatesFile
))
if
err
!=
nil
{
return
err
}
if
!
exists
{
cm
.
updates
=
[]
update
{}
}
else
{
var
bytes
[]
byte
bytes
,
err
=
ioutil
.
ReadFile
(
cm
.
path
(
updatesFile
))
if
err
!=
nil
{
return
err
}
if
err
=
json
.
Unmarshal
(
bytes
,
&
cm
.
updates
);
err
!=
nil
{
return
err
}
}
// Perform all new updates
for
i
:=
len
(
cm
.
updates
);
i
<
len
(
credentialManagerUpdates
);
i
++
{
err
=
credentialManagerUpdates
[
i
](
cm
)
update
:=
update
{
When
:
Timestamp
(
time
.
Now
()),
Number
:
i
,
Success
:
err
==
nil
,
}
if
err
!=
nil
{
str
:=
err
.
Error
()
update
.
Error
=
&
str
}
cm
.
updates
=
append
(
cm
.
updates
,
update
)
}
// Save updates file
bytes
,
err
:=
json
.
Marshal
(
cm
.
updates
)
if
err
!=
nil
{
return
err
}
saveFile
(
cm
.
path
(
updatesFile
),
bytes
)
return
nil
}
func
(
cm
*
CredentialManager
)
path
(
file
string
)
string
{
return
cm
.
storagePath
+
"/"
+
file
func
(
s
*
storage
)
path
(
p
string
)
string
{
return
s
.
storagePath
+
"/"
+
p
}
func
(
cm
*
CredentialMan
age
r
)
signatureFilename
(
attrs
*
AttributeList
)
string
{
func
(
s
*
stor
age
)
signatureFilename
(
attrs
*
AttributeList
)
string
{
// We take the SHA256 hash over all attributes as the filename for the signature.
// This means that the signatures of two credentials that have identical attributes
// will be written to the same file, one overwriting the other - but that doesn't
// matter, because either one of the signatures is valid over both attribute lists,
// so keeping one of them suffices.
return
cm
.
path
(
signaturesDir
)
+
"/"
+
attrs
.
hash
()
return
s
.
path
(
signaturesDir
)
+
"/"
+
attrs
.
hash
()
}
// ensureStorageExists initializes the credential storage folder,
...
...
@@ -218,36 +115,22 @@ func (cm *CredentialManager) signatureFilename(attrs *AttributeList) string {
// NOTE: we do not create the folder if it does not exist!
// Setting it up in a properly protected location (e.g., with automatic
// backups to iCloud/Google disabled) is the responsibility of the user.
func
(
cm
*
CredentialManager
)
ensureStorageExists
()
error
{
exist
,
err
:=
PathExists
(
cm
.
storagePath
)
if
err
!=
nil
{
return
err
}
if
!
exist
{
return
errors
.
New
(
"credential storage path does not exist"
)
}
if
exist
,
err
=
PathExists
(
cm
.
ConfigurationStore
.
path
);
err
!=
nil
{
func
(
s
*
storage
)
ensureStorageExists
()
error
{
if
err
:=
AssertPathExists
(
s
.
storagePath
);
err
!=
nil
{
return
err
}
if
!
exist
{
if
err
=
ensureDirectoryExists
(
cm
.
ConfigurationStore
.
path
);
err
!=
nil
{
return
err
}
cm
.
ConfigurationStore
.
Copy
(
cm
.
irmaConfigurationPath
,
false
)
}
return
ensureDirectoryExists
(
cm
.
path
(
signaturesDir
))
return
ensureDirectoryExists
(
s
.
path
(
signaturesDir
))
}
func
(
cm
*
CredentialMan
age
r
)
storeSecretKey
(
sk
*
secretKey
)
error
{
func
(
s
*
stor
age
)
storeSecretKey
(
sk
*
secretKey
)
error
{
bytes
,
err
:=
json
.
Marshal
(
sk
)
if
err
!=
nil
{
return
err
}
return
saveFile
(
cm
.
path
(
skFile
),
bytes
)
return
saveFile
(
s
.
path
(
skFile
),
bytes
)
}
func
(
cm
*
CredentialMan
age
r
)
storeSignature
(
cred
*
credential
,
counter
int
)
(
err
error
)
{
func
(
s
*
stor
age
)
storeSignature
(
cred
*
credential
)
(
err
error
)
{
if
cred
.
CredentialType
()
==
nil
{
return
errors
.
New
(
"cannot add unknown credential type"
)
}
...
...
@@ -257,61 +140,66 @@ func (cm *CredentialManager) storeSignature(cred *credential, counter int) (err
return
err
}
filename
:=
cm
.
signatureFilename
(
cred
.
AttributeList
())
filename
:=
s
.
signatureFilename
(
cred
.
AttributeList
())
err
=
saveFile
(
filename
,
credbytes
)
return
}
func
(
cm
*
CredentialManager
)
store
Attribute
s
(
)
error
{
func
(
s
*
storage
)
storeAttributes
(
attributes
map
[
CredentialTypeIdentifier
][]
*
Attribute
List
)
error
{
temp
:=
[]
*
AttributeList
{}
for
_
,
attrlistlist
:=
range
cm
.
attributes
{
for
_
,
attrlistlist
:=
range
attributes
{
for
_
,
attrlist
:=
range
attrlistlist
{
temp
=
append
(
temp
,
attrlist
)
}
}
if
attrbytes
,
err
:=
json
.
Marshal
(
temp
);
err
==
nil
{
return
saveFile
(
cm
.
path
(
attributesFile
),
attrbytes
)
return
saveFile
(
s
.
path
(
attributesFile
),
attrbytes
)
}
else
{
return
err
}
}
func
(
cm
*
CredentialMan
age
r
)
storeKeyshareServers
()
(
err
error
)
{
bts
,
err
:=
json
.
Marshal
(
cm
.
keyshareServers
)
func
(
s
*
stor
age
)
storeKeyshareServers
(
keyshareServers
map
[
SchemeManagerIdentifier
]
*
keyshareServer
)
(
err
error
)
{
bts
,
err
:=
json
.
Marshal
(
keyshareServers
)
if
err
!=
nil
{
return
}
err
=
saveFile
(
cm
.
path
(
kssFile
),
bts
)
err
=
saveFile
(
s
.
path
(
kssFile
),
bts
)
return
}
func
(
cm
*
CredentialMan
age
r
)
storePaillierKeys
()
(
err
error
)
{
bts
,
err
:=
json
.
Marshal
(
cm
.
paillierKeyCache
)
func
(
s
*
stor
age
)
storePaillierKeys
(
key
*
paillierPrivateKey
)
(
err
error
)
{
bts
,
err
:=
json
.
Marshal
(
key
)
if
err
!=
nil
{
return
}
err
=
saveFile
(
cm
.
path
(
paillierFile
),
bts
)
err
=
saveFile
(
s
.
path
(
paillierFile
),
bts
)
return
}
func
(
cm
*
CredentialMan
age
r
)
storeLogs
()
(
err
error
)
{
bts
,
err
:=
json
.
Marshal
(
cm
.
logs
)
func
(
s
*
stor
age
)
storeLogs
(
logs
[]
*
LogEntry
)
(
err
error
)
{
bts
,
err
:=
json
.
Marshal
(
logs
)
if
err
!=
nil
{
return
}
err
=
saveFile
(
cm
.
path
(
logsFile
),
bts
)
err
=
saveFile
(
s
.
path
(
logsFile
),
bts
)
return
}
func
(
cm
*
CredentialManager
)
loadSignature
(
attrs
*
AttributeList
)
(
signature
*
gabi
.
CLSignature
,
err
error
)
{
sigpath
:=
cm
.
signatureFilename
(
attrs
)
exists
,
err
:=
PathExists
(
sigpath
)
func
(
s
*
storage
)
storeUpdates
(
updates
[]
update
)
(
err
error
)
{
bts
,
err
:=
json
.
Marshal
(
updates
)
if
err
!=
nil
{
return
}
if
!
exists
{
return
nil
,
errors
.
New
(
"Signature file not found"
)
err
=
saveFile
(
s
.
path
(
updatesFile
),
bts
)
return
}
func
(
s
*
storage
)
loadSignature
(
attrs
*
AttributeList
)
(
signature
*
gabi
.
CLSignature
,
err
error
)
{
sigpath
:=
s
.
signatureFilename
(
attrs
)
if
err
:=
AssertPathExists
(
sigpath
);
err
!=
nil
{
return
nil
,
err
}
bytes
,
err
:=
ioutil
.
ReadFile
(
sigpath
)
if
err
!=
nil
{
...
...
@@ -324,16 +212,16 @@ func (cm *CredentialManager) loadSignature(attrs *AttributeList) (signature *gab
// loadSecretKey retrieves and returns the secret key from storage, or if no secret key
// was found in storage, it generates, saves, and returns a new secret key.
func
(
cm
*
CredentialMan
age
r
)
loadSecretKey
()
(
*
secretKey
,
error
)
{
func
(
s
*
stor
age
)
loadSecretKey
()
(
*
secretKey
,
error
)
{
sk
:=
&
secretKey
{}
var
err
error
exists
,
err
:=
PathExists
(
cm
.
path
(
skFile
))
exists
,
err
:=
PathExists
(
s
.
path
(
skFile
))
if
err
!=
nil
{
return
nil
,
err
}
if
exists
{
var
bytes
[]
byte
if
bytes
,
err
=
ioutil
.
ReadFile
(
cm
.
path
(
skFile
));
err
!=
nil
{
if
bytes
,
err
=
ioutil
.
ReadFile
(
s
.
path
(
skFile
));
err
!=
nil
{
return
nil
,
err
}
if
err
=
json
.
Unmarshal
(
bytes
,
sk
);
err
!=
nil
{
...
...
@@ -342,23 +230,23 @@ func (cm *CredentialManager) loadSecretKey() (*secretKey, error) {
return
sk
,
err
}
sk
,
err
=
cm
.
generateSecretKey
()
sk
,
err
=
generateSecretKey
()
if
err
!=
nil
{
return
nil
,
err
}
err
=
cm
.
storeSecretKey
(
sk
)
err
=
s
.
storeSecretKey
(
sk
)
if
err
!=
nil
{
return
nil
,
err
}
return
sk
,
nil
}