Move Linux client & common packages into a public repo.
This commit is contained in:
+149
@@ -0,0 +1,149 @@
|
||||
// Copyright (c) 2020 Tailscale Inc & AUTHORS All rights reserved.
|
||||
// Use of this source code is governed by a BSD-style
|
||||
// license that can be found in the LICENSE file.
|
||||
|
||||
package ipn
|
||||
|
||||
import (
|
||||
"bytes"
|
||||
"encoding/json"
|
||||
"fmt"
|
||||
"io/ioutil"
|
||||
"log"
|
||||
"os"
|
||||
"path/filepath"
|
||||
|
||||
"tailscale.com/atomicfile"
|
||||
"tailscale.com/control/controlclient"
|
||||
)
|
||||
|
||||
type Prefs struct {
|
||||
RouteAll bool
|
||||
AllowSingleHosts bool
|
||||
CorpDNS bool
|
||||
WantRunning bool
|
||||
NotepadURLs bool
|
||||
UsePacketFilter bool
|
||||
|
||||
// The Persist field is named 'Config' in the file for backward
|
||||
// compatibility with earlier versions.
|
||||
// TODO(apenwarr): We should move this out of here, it's not a pref.
|
||||
// We can maybe do that once we're sure which module should persist
|
||||
// it (backend or frontend?)
|
||||
Persist *controlclient.Persist `json:"Config"`
|
||||
}
|
||||
|
||||
func (uc *Prefs) Pretty() string {
|
||||
var ucp string
|
||||
if uc.Persist != nil {
|
||||
ucp = uc.Persist.Pretty()
|
||||
} else {
|
||||
ucp = "Persist=nil"
|
||||
}
|
||||
return fmt.Sprintf("Prefs{ra=%v mesh=%v dns=%v want=%v notepad=%v %v}",
|
||||
uc.RouteAll, uc.AllowSingleHosts, uc.CorpDNS, uc.WantRunning,
|
||||
uc.NotepadURLs, ucp)
|
||||
}
|
||||
|
||||
func (uc *Prefs) ToBytes() []byte {
|
||||
data, err := json.MarshalIndent(uc, "", "\t")
|
||||
if err != nil {
|
||||
log.Fatalf("Prefs marshal: %v\n", err)
|
||||
}
|
||||
return data
|
||||
}
|
||||
|
||||
func (uc *Prefs) Equals(uc2 *Prefs) bool {
|
||||
b1 := uc.ToBytes()
|
||||
b2 := uc2.ToBytes()
|
||||
return bytes.Equal(b1, b2)
|
||||
}
|
||||
|
||||
func NewPrefs() Prefs {
|
||||
return Prefs{
|
||||
// Provide default values for options which are normally
|
||||
// true, but might be missing from the json data for any
|
||||
// reason. The json can still override them to false.
|
||||
RouteAll: true,
|
||||
AllowSingleHosts: true,
|
||||
CorpDNS: true,
|
||||
WantRunning: true,
|
||||
UsePacketFilter: true,
|
||||
}
|
||||
}
|
||||
|
||||
func PrefsFromBytes(b []byte, enforceDefaults bool) (Prefs, error) {
|
||||
uc := NewPrefs()
|
||||
if len(b) == 0 {
|
||||
return uc, nil
|
||||
}
|
||||
persist := &controlclient.Persist{}
|
||||
err := json.Unmarshal(b, persist)
|
||||
if err == nil && (persist.Provider != "" || persist.LoginName != "") {
|
||||
// old-style relaynode config; import it
|
||||
uc.Persist = persist
|
||||
} else {
|
||||
err = json.Unmarshal(b, &uc)
|
||||
if err != nil {
|
||||
log.Printf("Prefs parse: %v: %v\n", err, b)
|
||||
}
|
||||
}
|
||||
if enforceDefaults {
|
||||
uc.RouteAll = true
|
||||
uc.AllowSingleHosts = true
|
||||
}
|
||||
return uc, err
|
||||
}
|
||||
|
||||
func (uc *Prefs) Copy() *Prefs {
|
||||
uc2, err := PrefsFromBytes(uc.ToBytes(), false)
|
||||
if err != nil {
|
||||
log.Fatalf("Prefs was uncopyable: %v\n", err)
|
||||
}
|
||||
return &uc2
|
||||
}
|
||||
|
||||
func LoadPrefs(filename string, enforceDefaults bool) Prefs {
|
||||
log.Printf("Loading prefs %v\n", filename)
|
||||
data, err := ioutil.ReadFile(filename)
|
||||
uc := NewPrefs()
|
||||
if err != nil {
|
||||
log.Printf("Read: %v: %v\n", filename, err)
|
||||
goto fail
|
||||
}
|
||||
uc, err = PrefsFromBytes(data, enforceDefaults)
|
||||
if err != nil {
|
||||
log.Printf("Parse: %v: %v\n", filename, err)
|
||||
goto fail
|
||||
}
|
||||
goto post
|
||||
fail:
|
||||
log.Printf("failed to load config. Generating a new one.\n")
|
||||
uc = NewPrefs()
|
||||
uc.WantRunning = true
|
||||
post:
|
||||
// Update: we changed our minds :)
|
||||
// Versabank would like to persist the setting across reboots, for now,
|
||||
// because they don't fully trust the system and want to be able to
|
||||
// leave it turned off when not in use. Eventually we need to make
|
||||
// all motivation for this go away.
|
||||
if false {
|
||||
// Usability note: we always want WantRunning = true on startup.
|
||||
// That way, if someone accidentally disables their VPN and doesn't
|
||||
// know how, rebooting will fix it.
|
||||
// We still persist WantRunning just in case we change our minds on
|
||||
// this topic.
|
||||
uc.WantRunning = true
|
||||
}
|
||||
log.Printf("Loaded prefs %v %v\n", filename, uc.Pretty())
|
||||
return uc
|
||||
}
|
||||
|
||||
func SavePrefs(filename string, uc *Prefs) {
|
||||
log.Printf("Saving prefs %v %v\n", filename, uc.Pretty())
|
||||
data := uc.ToBytes()
|
||||
os.MkdirAll(filepath.Dir(filename), 0700)
|
||||
if err := atomicfile.WriteFile(filename, data, 0666); err != nil {
|
||||
log.Printf("SavePrefs: %v\n", err)
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user