newline battles continue
This commit is contained in:
1346
vendor/github.com/ncw/rclone/fs/config/config.go
generated
vendored
Executable file
1346
vendor/github.com/ncw/rclone/fs/config/config.go
generated
vendored
Executable file
File diff suppressed because it is too large
Load Diff
10
vendor/github.com/ncw/rclone/fs/config/config_other.go
generated
vendored
Executable file
10
vendor/github.com/ncw/rclone/fs/config/config_other.go
generated
vendored
Executable file
@@ -0,0 +1,10 @@
|
||||
// Read, write and edit the config file
|
||||
// Non-unix specific functions.
|
||||
|
||||
// +build !darwin,!dragonfly,!freebsd,!linux,!netbsd,!openbsd,!solaris
|
||||
|
||||
package config
|
||||
|
||||
// attemptCopyGroups tries to keep the group the same, which only makes sense
|
||||
// for system with user-group-world permission model.
|
||||
func attemptCopyGroup(fromPath, toPath string) {}
|
||||
29
vendor/github.com/ncw/rclone/fs/config/config_read_password.go
generated
vendored
Executable file
29
vendor/github.com/ncw/rclone/fs/config/config_read_password.go
generated
vendored
Executable file
@@ -0,0 +1,29 @@
|
||||
// ReadPassword for OSes which are supported by golang.org/x/crypto/ssh/terminal
|
||||
// See https://github.com/golang/go/issues/14441 - plan9
|
||||
// https://github.com/golang/go/issues/13085 - solaris
|
||||
|
||||
// +build !solaris,!plan9
|
||||
|
||||
package config
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"log"
|
||||
"os"
|
||||
|
||||
"golang.org/x/crypto/ssh/terminal"
|
||||
)
|
||||
|
||||
// ReadPassword reads a password without echoing it to the terminal.
|
||||
func ReadPassword() string {
|
||||
stdin := int(os.Stdin.Fd())
|
||||
if !terminal.IsTerminal(stdin) {
|
||||
return ReadLine()
|
||||
}
|
||||
line, err := terminal.ReadPassword(stdin)
|
||||
_, _ = fmt.Fprintln(os.Stderr)
|
||||
if err != nil {
|
||||
log.Fatalf("Failed to read password: %v", err)
|
||||
}
|
||||
return string(line)
|
||||
}
|
||||
12
vendor/github.com/ncw/rclone/fs/config/config_read_password_unsupported.go
generated
vendored
Executable file
12
vendor/github.com/ncw/rclone/fs/config/config_read_password_unsupported.go
generated
vendored
Executable file
@@ -0,0 +1,12 @@
|
||||
// ReadPassword for OSes which are not supported by golang.org/x/crypto/ssh/terminal
|
||||
// See https://github.com/golang/go/issues/14441 - plan9
|
||||
// https://github.com/golang/go/issues/13085 - solaris
|
||||
|
||||
// +build solaris plan9
|
||||
|
||||
package config
|
||||
|
||||
// ReadPassword reads a password with echoing it to the terminal.
|
||||
func ReadPassword() string {
|
||||
return ReadLine()
|
||||
}
|
||||
37
vendor/github.com/ncw/rclone/fs/config/config_unix.go
generated
vendored
Executable file
37
vendor/github.com/ncw/rclone/fs/config/config_unix.go
generated
vendored
Executable file
@@ -0,0 +1,37 @@
|
||||
// Read, write and edit the config file
|
||||
// Unix specific functions.
|
||||
|
||||
// +build darwin dragonfly freebsd linux netbsd openbsd solaris
|
||||
|
||||
package config
|
||||
|
||||
import (
|
||||
"os"
|
||||
"os/user"
|
||||
"strconv"
|
||||
"syscall"
|
||||
|
||||
"github.com/ncw/rclone/fs"
|
||||
)
|
||||
|
||||
// attemptCopyGroups tries to keep the group the same. User will be the one
|
||||
// who is currently running this process.
|
||||
func attemptCopyGroup(fromPath, toPath string) {
|
||||
info, err := os.Stat(fromPath)
|
||||
if err != nil || info.Sys() == nil {
|
||||
return
|
||||
}
|
||||
if stat, ok := info.Sys().(*syscall.Stat_t); ok {
|
||||
uid := int(stat.Uid)
|
||||
// prefer self over previous owner of file, because it has a higher chance
|
||||
// of success
|
||||
if user, err := user.Current(); err == nil {
|
||||
if tmpUID, err := strconv.Atoi(user.Uid); err == nil {
|
||||
uid = tmpUID
|
||||
}
|
||||
}
|
||||
if err = os.Chown(toPath, uid, int(stat.Gid)); err != nil {
|
||||
fs.Debugf(nil, "Failed to keep previous owner of config file: %v", err)
|
||||
}
|
||||
}
|
||||
}
|
||||
86
vendor/github.com/ncw/rclone/fs/config/configmap/configmap.go
generated
vendored
Executable file
86
vendor/github.com/ncw/rclone/fs/config/configmap/configmap.go
generated
vendored
Executable file
@@ -0,0 +1,86 @@
|
||||
// Package configmap provides an abstraction for reading and writing config
|
||||
package configmap
|
||||
|
||||
// Getter provides an interface to get config items
|
||||
type Getter interface {
|
||||
// Get should get an item with the key passed in and return
|
||||
// the value. If the item is found then it should return true,
|
||||
// otherwise false.
|
||||
Get(key string) (value string, ok bool)
|
||||
}
|
||||
|
||||
// Setter provides an interface to set config items
|
||||
type Setter interface {
|
||||
// Set should set an item into persistent config store.
|
||||
Set(key, value string)
|
||||
}
|
||||
|
||||
// Mapper provides an interface to read and write config
|
||||
type Mapper interface {
|
||||
Getter
|
||||
Setter
|
||||
}
|
||||
|
||||
// Map provides a wrapper around multiple Setter and
|
||||
// Getter interfaces.
|
||||
type Map struct {
|
||||
setters []Setter
|
||||
getters []Getter
|
||||
}
|
||||
|
||||
// New returns an empty Map
|
||||
func New() *Map {
|
||||
return &Map{}
|
||||
}
|
||||
|
||||
// AddGetter appends a getter onto the end of the getters
|
||||
func (c *Map) AddGetter(getter Getter) *Map {
|
||||
c.getters = append(c.getters, getter)
|
||||
return c
|
||||
}
|
||||
|
||||
// AddGetters appends multiple getters onto the end of the getters
|
||||
func (c *Map) AddGetters(getters ...Getter) *Map {
|
||||
c.getters = append(c.getters, getters...)
|
||||
return c
|
||||
}
|
||||
|
||||
// AddSetter appends a setter onto the end of the setters
|
||||
func (c *Map) AddSetter(setter Setter) *Map {
|
||||
c.setters = append(c.setters, setter)
|
||||
return c
|
||||
}
|
||||
|
||||
// Get gets an item with the key passed in and return the value from
|
||||
// the first getter. If the item is found then it returns true,
|
||||
// otherwise false.
|
||||
func (c *Map) Get(key string) (value string, ok bool) {
|
||||
for _, do := range c.getters {
|
||||
value, ok = do.Get(key)
|
||||
if ok {
|
||||
return value, ok
|
||||
}
|
||||
}
|
||||
return "", false
|
||||
}
|
||||
|
||||
// Set sets an item into all the stored setters.
|
||||
func (c *Map) Set(key, value string) {
|
||||
for _, do := range c.setters {
|
||||
do.Set(key, value)
|
||||
}
|
||||
}
|
||||
|
||||
// Simple is a simple Mapper for testing
|
||||
type Simple map[string]string
|
||||
|
||||
// Get the value
|
||||
func (c Simple) Get(key string) (value string, ok bool) {
|
||||
value, ok = c[key]
|
||||
return value, ok
|
||||
}
|
||||
|
||||
// Set the value
|
||||
func (c Simple) Set(key, value string) {
|
||||
c[key] = value
|
||||
}
|
||||
127
vendor/github.com/ncw/rclone/fs/config/configstruct/configstruct.go
generated
vendored
Executable file
127
vendor/github.com/ncw/rclone/fs/config/configstruct/configstruct.go
generated
vendored
Executable file
@@ -0,0 +1,127 @@
|
||||
// Package configstruct parses unstructured maps into structures
|
||||
package configstruct
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"reflect"
|
||||
"regexp"
|
||||
"strings"
|
||||
|
||||
"github.com/ncw/rclone/fs/config/configmap"
|
||||
"github.com/pkg/errors"
|
||||
)
|
||||
|
||||
var matchUpper = regexp.MustCompile("([A-Z]+)")
|
||||
|
||||
// camelToSnake converts CamelCase to snake_case
|
||||
func camelToSnake(in string) string {
|
||||
out := matchUpper.ReplaceAllString(in, "_$1")
|
||||
out = strings.ToLower(out)
|
||||
out = strings.Trim(out, "_")
|
||||
return out
|
||||
}
|
||||
|
||||
// StringToInterface turns in into an interface{} the same type as def
|
||||
func StringToInterface(def interface{}, in string) (newValue interface{}, err error) {
|
||||
typ := reflect.TypeOf(def)
|
||||
switch typ.Kind() {
|
||||
case reflect.String:
|
||||
// Pass strings unmodified
|
||||
return in, nil
|
||||
}
|
||||
// Otherwise parse with Sscanln
|
||||
//
|
||||
// This means any types we use here must implement fmt.Scanner
|
||||
o := reflect.New(typ)
|
||||
n, err := fmt.Sscanln(in, o.Interface())
|
||||
if err != nil {
|
||||
return newValue, errors.Wrapf(err, "parsing %q as %T failed", in, def)
|
||||
}
|
||||
if n != 1 {
|
||||
return newValue, errors.New("no items parsed")
|
||||
}
|
||||
return o.Elem().Interface(), nil
|
||||
}
|
||||
|
||||
// Item descripts a single entry in the options structure
|
||||
type Item struct {
|
||||
Name string // snake_case
|
||||
Field string // CamelCase
|
||||
Num int // number of the field in the struct
|
||||
Value interface{}
|
||||
}
|
||||
|
||||
// Items parses the opt struct and returns a slice of Item objects.
|
||||
//
|
||||
// opt must be a pointer to a struct. The struct should have entirely
|
||||
// public fields.
|
||||
//
|
||||
// The config_name is looked up in a struct tag called "config" or if
|
||||
// not found is the field name converted from CamelCase to snake_case.
|
||||
func Items(opt interface{}) (items []Item, err error) {
|
||||
def := reflect.ValueOf(opt)
|
||||
if def.Kind() != reflect.Ptr {
|
||||
return nil, errors.New("argument must be a pointer")
|
||||
}
|
||||
def = def.Elem() // indirect the pointer
|
||||
if def.Kind() != reflect.Struct {
|
||||
return nil, errors.New("argument must be a pointer to a struct")
|
||||
}
|
||||
defType := def.Type()
|
||||
for i := 0; i < def.NumField(); i++ {
|
||||
field := defType.Field(i)
|
||||
fieldName := field.Name
|
||||
configName, ok := field.Tag.Lookup("config")
|
||||
if !ok {
|
||||
configName = camelToSnake(fieldName)
|
||||
}
|
||||
defaultItem := Item{
|
||||
Name: configName,
|
||||
Field: fieldName,
|
||||
Num: i,
|
||||
Value: def.Field(i).Interface(),
|
||||
}
|
||||
items = append(items, defaultItem)
|
||||
}
|
||||
return items, nil
|
||||
}
|
||||
|
||||
// Set interprets the field names in defaults and looks up config
|
||||
// values in the config passed in. Any values found in config will be
|
||||
// set in the opt structure.
|
||||
//
|
||||
// opt must be a pointer to a struct. The struct should have entirely
|
||||
// public fields. The field names are converted from CamelCase to
|
||||
// snake_case and looked up in the config supplied or a
|
||||
// `config:"field_name"` is looked up.
|
||||
//
|
||||
// If items are found then they are converted from string to native
|
||||
// types and set in opt.
|
||||
//
|
||||
// All the field types in the struct must implement fmt.Scanner.
|
||||
func Set(config configmap.Getter, opt interface{}) (err error) {
|
||||
defaultItems, err := Items(opt)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
defStruct := reflect.ValueOf(opt).Elem()
|
||||
for _, defaultItem := range defaultItems {
|
||||
newValue := defaultItem.Value
|
||||
if configValue, ok := config.Get(defaultItem.Name); ok {
|
||||
var newNewValue interface{}
|
||||
newNewValue, err = StringToInterface(newValue, configValue)
|
||||
if err != nil {
|
||||
// Mask errors if setting an empty string as
|
||||
// it isn't valid for all types. This makes
|
||||
// empty string be the equivalent of unset.
|
||||
if configValue != "" {
|
||||
return errors.Wrapf(err, "couldn't parse config item %q = %q as %T", defaultItem.Name, configValue, defaultItem.Value)
|
||||
}
|
||||
} else {
|
||||
newValue = newNewValue
|
||||
}
|
||||
}
|
||||
defStruct.Field(defaultItem.Num).Set(reflect.ValueOf(newValue))
|
||||
}
|
||||
return nil
|
||||
}
|
||||
94
vendor/github.com/ncw/rclone/fs/config/obscure/obscure.go
generated
vendored
Executable file
94
vendor/github.com/ncw/rclone/fs/config/obscure/obscure.go
generated
vendored
Executable file
@@ -0,0 +1,94 @@
|
||||
// Package obscure contains the Obscure and Reveal commands
|
||||
package obscure
|
||||
|
||||
import (
|
||||
"crypto/aes"
|
||||
"crypto/cipher"
|
||||
"crypto/rand"
|
||||
"encoding/base64"
|
||||
"io"
|
||||
"log"
|
||||
|
||||
"github.com/pkg/errors"
|
||||
)
|
||||
|
||||
// crypt internals
|
||||
var (
|
||||
cryptKey = []byte{
|
||||
0x9c, 0x93, 0x5b, 0x48, 0x73, 0x0a, 0x55, 0x4d,
|
||||
0x6b, 0xfd, 0x7c, 0x63, 0xc8, 0x86, 0xa9, 0x2b,
|
||||
0xd3, 0x90, 0x19, 0x8e, 0xb8, 0x12, 0x8a, 0xfb,
|
||||
0xf4, 0xde, 0x16, 0x2b, 0x8b, 0x95, 0xf6, 0x38,
|
||||
}
|
||||
cryptBlock cipher.Block
|
||||
cryptRand = rand.Reader
|
||||
)
|
||||
|
||||
// crypt transforms in to out using iv under AES-CTR.
|
||||
//
|
||||
// in and out may be the same buffer.
|
||||
//
|
||||
// Note encryption and decryption are the same operation
|
||||
func crypt(out, in, iv []byte) error {
|
||||
if cryptBlock == nil {
|
||||
var err error
|
||||
cryptBlock, err = aes.NewCipher(cryptKey)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
}
|
||||
stream := cipher.NewCTR(cryptBlock, iv)
|
||||
stream.XORKeyStream(out, in)
|
||||
return nil
|
||||
}
|
||||
|
||||
// Obscure a value
|
||||
//
|
||||
// This is done by encrypting with AES-CTR
|
||||
func Obscure(x string) (string, error) {
|
||||
plaintext := []byte(x)
|
||||
ciphertext := make([]byte, aes.BlockSize+len(plaintext))
|
||||
iv := ciphertext[:aes.BlockSize]
|
||||
if _, err := io.ReadFull(cryptRand, iv); err != nil {
|
||||
return "", errors.Wrap(err, "failed to read iv")
|
||||
}
|
||||
if err := crypt(ciphertext[aes.BlockSize:], plaintext, iv); err != nil {
|
||||
return "", errors.Wrap(err, "encrypt failed")
|
||||
}
|
||||
return base64.RawURLEncoding.EncodeToString(ciphertext), nil
|
||||
}
|
||||
|
||||
// MustObscure obscures a value, exiting with a fatal error if it failed
|
||||
func MustObscure(x string) string {
|
||||
out, err := Obscure(x)
|
||||
if err != nil {
|
||||
log.Fatalf("Obscure failed: %v", err)
|
||||
}
|
||||
return out
|
||||
}
|
||||
|
||||
// Reveal an obscured value
|
||||
func Reveal(x string) (string, error) {
|
||||
ciphertext, err := base64.RawURLEncoding.DecodeString(x)
|
||||
if err != nil {
|
||||
return "", errors.Wrap(err, "base64 decode failed when revealing password - is it obscured?")
|
||||
}
|
||||
if len(ciphertext) < aes.BlockSize {
|
||||
return "", errors.New("input too short when revealing password - is it obscured?")
|
||||
}
|
||||
buf := ciphertext[aes.BlockSize:]
|
||||
iv := ciphertext[:aes.BlockSize]
|
||||
if err := crypt(buf, buf, iv); err != nil {
|
||||
return "", errors.Wrap(err, "decrypt failed when revealing password - is it obscured?")
|
||||
}
|
||||
return string(buf), nil
|
||||
}
|
||||
|
||||
// MustReveal reveals an obscured value, exiting with a fatal error if it failed
|
||||
func MustReveal(x string) string {
|
||||
out, err := Reveal(x)
|
||||
if err != nil {
|
||||
log.Fatalf("Reveal failed: %v", err)
|
||||
}
|
||||
return out
|
||||
}
|
||||
Reference in New Issue
Block a user