| 
									
										
										
										
											2014-12-31 15:39:33 +01:00
										 |  |  | /* | 
					
						
							|  |  |  | 	This file is part of go-ethereum | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | 	go-ethereum is free software: you can redistribute it and/or modify | 
					
						
							|  |  |  | 	it under the terms of the GNU Lesser General Public License as published by | 
					
						
							|  |  |  | 	the Free Software Foundation, either version 3 of the License, or | 
					
						
							|  |  |  | 	(at your option) any later version. | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | 	go-ethereum is distributed in the hope that it will be useful, | 
					
						
							|  |  |  | 	but WITHOUT ANY WARRANTY; without even the implied warranty of | 
					
						
							|  |  |  | 	MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the | 
					
						
							|  |  |  | 	GNU General Public License for more details. | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | 	You should have received a copy of the GNU Lesser General Public License | 
					
						
							|  |  |  | 	along with go-ethereum.  If not, see <http://www.gnu.org/licenses/>. | 
					
						
							|  |  |  | */ | 
					
						
							|  |  |  | /** | 
					
						
							|  |  |  |  * @authors | 
					
						
							|  |  |  |  * 	Gustav Simonsson <gustav.simonsson@gmail.com> | 
					
						
							|  |  |  |  * @date 2015 | 
					
						
							|  |  |  |  * | 
					
						
							|  |  |  |  */ | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | package crypto | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | import ( | 
					
						
							| 
									
										
										
										
											2015-01-25 02:07:20 +01:00
										 |  |  | 	"encoding/hex" | 
					
						
							| 
									
										
										
										
											2014-12-31 15:39:33 +01:00
										 |  |  | 	"encoding/json" | 
					
						
							|  |  |  | 	"fmt" | 
					
						
							| 
									
										
										
										
											2015-01-15 17:45:45 +01:00
										 |  |  | 	"io" | 
					
						
							| 
									
										
										
										
											2014-12-31 15:39:33 +01:00
										 |  |  | 	"io/ioutil" | 
					
						
							|  |  |  | 	"os" | 
					
						
							|  |  |  | 	"path" | 
					
						
							|  |  |  | ) | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | // TODO: rename to KeyStore when replacing existing KeyStore | 
					
						
							|  |  |  | type KeyStore2 interface { | 
					
						
							| 
									
										
										
										
											2015-01-15 17:45:45 +01:00
										 |  |  | 	// create new key using io.Reader entropy source and optionally using auth string | 
					
						
							|  |  |  | 	GenerateNewKey(io.Reader, string) (*Key, error) | 
					
						
							| 
									
										
										
										
											2015-01-25 02:07:20 +01:00
										 |  |  | 	GetKey([]byte, string) (*Key, error) // key from addr and auth string | 
					
						
							|  |  |  | 	GetKeyAddresses() ([][]byte, error)  // get all addresses | 
					
						
							|  |  |  | 	StoreKey(*Key, string) error         // store key optionally using auth string | 
					
						
							|  |  |  | 	DeleteKey([]byte, string) error      // delete key by addr and auth string | 
					
						
							| 
									
										
										
										
											2014-12-31 15:39:33 +01:00
										 |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2015-01-07 16:06:26 +01:00
										 |  |  | type keyStorePlain struct { | 
					
						
							| 
									
										
										
										
											2014-12-31 15:39:33 +01:00
										 |  |  | 	keysDirPath string | 
					
						
							|  |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2015-01-07 16:06:26 +01:00
										 |  |  | func NewKeyStorePlain(path string) KeyStore2 { | 
					
						
							| 
									
										
										
										
											2015-01-19 22:12:22 +01:00
										 |  |  | 	return &keyStorePlain{path} | 
					
						
							| 
									
										
										
										
											2015-01-07 16:06:26 +01:00
										 |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2015-01-15 17:45:45 +01:00
										 |  |  | func (ks keyStorePlain) GenerateNewKey(rand io.Reader, auth string) (key *Key, err error) { | 
					
						
							|  |  |  | 	return GenerateNewKeyDefault(ks, rand, auth) | 
					
						
							| 
									
										
										
										
											2014-12-31 15:39:33 +01:00
										 |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2015-01-15 17:45:45 +01:00
										 |  |  | func GenerateNewKeyDefault(ks KeyStore2, rand io.Reader, auth string) (key *Key, err error) { | 
					
						
							| 
									
										
										
										
											2014-12-31 15:39:33 +01:00
										 |  |  | 	defer func() { | 
					
						
							|  |  |  | 		if r := recover(); r != nil { | 
					
						
							|  |  |  | 			err = fmt.Errorf("GenerateNewKey error: %v", r) | 
					
						
							|  |  |  | 		} | 
					
						
							|  |  |  | 	}() | 
					
						
							| 
									
										
										
										
											2015-01-15 17:45:45 +01:00
										 |  |  | 	key = NewKey(rand) | 
					
						
							| 
									
										
										
										
											2014-12-31 15:39:33 +01:00
										 |  |  | 	err = ks.StoreKey(key, auth) | 
					
						
							| 
									
										
										
										
											2015-01-07 16:06:26 +01:00
										 |  |  | 	return key, err | 
					
						
							| 
									
										
										
										
											2014-12-31 15:39:33 +01:00
										 |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2015-01-25 02:07:20 +01:00
										 |  |  | func (ks keyStorePlain) GetKey(keyAddr []byte, auth string) (key *Key, err error) { | 
					
						
							|  |  |  | 	fileContent, err := GetKeyFile(ks.keysDirPath, keyAddr) | 
					
						
							| 
									
										
										
										
											2014-12-31 15:39:33 +01:00
										 |  |  | 	if err != nil { | 
					
						
							| 
									
										
										
										
											2015-01-07 16:06:26 +01:00
										 |  |  | 		return nil, err | 
					
						
							| 
									
										
										
										
											2014-12-31 15:39:33 +01:00
										 |  |  | 	} | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | 	key = new(Key) | 
					
						
							|  |  |  | 	err = json.Unmarshal(fileContent, key) | 
					
						
							| 
									
										
										
										
											2015-01-07 16:06:26 +01:00
										 |  |  | 	return key, err | 
					
						
							| 
									
										
										
										
											2014-12-31 15:39:33 +01:00
										 |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2015-01-25 02:07:20 +01:00
										 |  |  | func (ks keyStorePlain) GetKeyAddresses() (addresses [][]byte, err error) { | 
					
						
							|  |  |  | 	return GetKeyAddresses(ks.keysDirPath) | 
					
						
							|  |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2015-01-07 16:06:26 +01:00
										 |  |  | func (ks keyStorePlain) StoreKey(key *Key, auth string) (err error) { | 
					
						
							| 
									
										
										
										
											2014-12-31 15:39:33 +01:00
										 |  |  | 	keyJSON, err := json.Marshal(key) | 
					
						
							|  |  |  | 	if err != nil { | 
					
						
							| 
									
										
										
										
											2015-01-07 16:06:26 +01:00
										 |  |  | 		return err | 
					
						
							| 
									
										
										
										
											2014-12-31 15:39:33 +01:00
										 |  |  | 	} | 
					
						
							| 
									
										
										
										
											2015-01-25 02:07:20 +01:00
										 |  |  | 	err = WriteKeyFile(key.Address, ks.keysDirPath, keyJSON) | 
					
						
							| 
									
										
										
										
											2015-01-07 16:06:26 +01:00
										 |  |  | 	return err | 
					
						
							| 
									
										
										
										
											2014-12-31 15:39:33 +01:00
										 |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2015-01-25 02:07:20 +01:00
										 |  |  | func (ks keyStorePlain) DeleteKey(keyAddr []byte, auth string) (err error) { | 
					
						
							|  |  |  | 	keyDirPath := path.Join(ks.keysDirPath, hex.EncodeToString(keyAddr)) | 
					
						
							| 
									
										
										
										
											2014-12-31 15:39:33 +01:00
										 |  |  | 	err = os.RemoveAll(keyDirPath) | 
					
						
							| 
									
										
										
										
											2015-01-07 16:06:26 +01:00
										 |  |  | 	return err | 
					
						
							| 
									
										
										
										
											2014-12-31 15:39:33 +01:00
										 |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2015-01-25 02:07:20 +01:00
										 |  |  | func GetKeyFile(keysDirPath string, keyAddr []byte) (fileContent []byte, err error) { | 
					
						
							|  |  |  | 	fileName := hex.EncodeToString(keyAddr) | 
					
						
							|  |  |  | 	return ioutil.ReadFile(path.Join(keysDirPath, fileName, fileName)) | 
					
						
							| 
									
										
										
										
											2014-12-31 15:39:33 +01:00
										 |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2015-01-25 02:07:20 +01:00
										 |  |  | func WriteKeyFile(addr []byte, keysDirPath string, content []byte) (err error) { | 
					
						
							|  |  |  | 	addrHex := hex.EncodeToString(addr) | 
					
						
							|  |  |  | 	keyDirPath := path.Join(keysDirPath, addrHex) | 
					
						
							|  |  |  | 	keyFilePath := path.Join(keyDirPath, addrHex) | 
					
						
							| 
									
										
										
										
											2014-12-31 15:39:33 +01:00
										 |  |  | 	err = os.MkdirAll(keyDirPath, 0700) // read, write and dir search for user | 
					
						
							|  |  |  | 	if err != nil { | 
					
						
							| 
									
										
										
										
											2015-01-07 16:06:26 +01:00
										 |  |  | 		return err | 
					
						
							| 
									
										
										
										
											2014-12-31 15:39:33 +01:00
										 |  |  | 	} | 
					
						
							| 
									
										
										
										
											2015-01-07 16:06:26 +01:00
										 |  |  | 	return ioutil.WriteFile(keyFilePath, content, 0600) // read, write for user | 
					
						
							| 
									
										
										
										
											2014-12-31 15:39:33 +01:00
										 |  |  | } | 
					
						
							| 
									
										
										
										
											2015-01-25 02:07:20 +01:00
										 |  |  | 
 | 
					
						
							|  |  |  | func GetKeyAddresses(keysDirPath string) (addresses [][]byte, err error) { | 
					
						
							|  |  |  | 	fileInfos, err := ioutil.ReadDir(keysDirPath) | 
					
						
							|  |  |  | 	if err != nil { | 
					
						
							|  |  |  | 		return nil, err | 
					
						
							|  |  |  | 	} | 
					
						
							|  |  |  | 	addresses = make([][]byte, len(fileInfos)) | 
					
						
							|  |  |  | 	for i, fileInfo := range fileInfos { | 
					
						
							| 
									
										
										
										
											2015-02-24 18:03:10 +01:00
										 |  |  | 		address, err := hex.DecodeString(fileInfo.Name()) | 
					
						
							|  |  |  | 		if err != nil { | 
					
						
							|  |  |  | 			continue | 
					
						
							|  |  |  | 		} | 
					
						
							|  |  |  | 		addresses[i] = address | 
					
						
							| 
									
										
										
										
											2015-01-25 02:07:20 +01:00
										 |  |  | 	} | 
					
						
							|  |  |  | 	return addresses, err | 
					
						
							|  |  |  | } |