CLI,proto,service: templates loading,DB backup&restore

This commit is contained in:
MaMe82 2018-10-24 09:44:58 +02:00
parent a8169f46d0
commit 984c3fdd5f
14 changed files with 1154 additions and 518 deletions

View File

@ -79,6 +79,7 @@ installkali:
cp -R dist/scripts /usr/local/P4wnP1/
cp -R dist/HIDScripts /usr/local/P4wnP1/
cp -R dist/www /usr/local/P4wnP1/
cp -R dist/db /usr/local/P4wnP1/
cp build/webapp.js /usr/local/P4wnP1/www
cp build/webapp.js.map /usr/local/P4wnP1/www
@ -102,6 +103,7 @@ install:
cp -R dist/scripts /usr/local/P4wnP1/
cp -R dist/HIDScripts /usr/local/P4wnP1/
cp -R dist/www /usr/local/P4wnP1/
cp -R dist/db /usr/local/P4wnP1/
cp dist/bin/* /usr/local/bin/
cp build/webapp.js /usr/local/P4wnP1/www
cp build/webapp.js.map /usr/local/P4wnP1/www

97
cli_client/cmd_db.go Normal file
View File

@ -0,0 +1,97 @@
package cli_client
import (
"encoding/json"
"fmt"
"github.com/spf13/cobra"
"os"
)
var (
// deploy
tmpDBBackupName = ""
)
func init() {
cmdDB := &cobra.Command{
Use: "db",
Short: "Database backup and restore",
}
cmdDBBackup := &cobra.Command{
Use: "backup",
Short: "Backup DB",
Run: func(cmd *cobra.Command, args []string) {
if len(tmpDBBackupName) == 0 {
fmt.Println("A name for the backup has to be provided with the '--name' flag")
os.Exit(-1)
}
fmt.Print("Creating backup ...")
err := ClientDBBackup(TIMEOUT_LONG, StrRemoteHost, StrRemotePort, tmpDBBackupName)
if err != nil {
fmt.Println(" failed")
fmt.Println(err.Error())
os.Exit(-1)
}
fmt.Println(" success")
},
}
cmdDBRestore := &cobra.Command{
Use: "restore",
Short: "Restore DB",
Run: func(cmd *cobra.Command, args []string) {
if len(tmpDBBackupName) == 0 {
fmt.Println("A name for the backup has to be provided with the '--name' flag")
os.Exit(-1)
}
fmt.Print("Restoring ...")
err := ClientDBRestore(TIMEOUT_LONG, StrRemoteHost, StrRemotePort, tmpDBBackupName)
if err != nil {
fmt.Println(" failed")
fmt.Println(err.Error())
os.Exit(-1)
}
fmt.Println(" success")
},
}
cmdDBList := &cobra.Command{
Use: "list",
Short: "List backups",
Long: ``,
Run: func(cmd *cobra.Command, args []string) {
list,err := ClientDBList(TIMEOUT_LONG, StrRemoteHost, StrRemotePort)
if err != nil {
fmt.Println(err.Error())
os.Exit(-1)
}
if BoolJson {
b, err := json.Marshal(list)
if err == nil {
fmt.Println(string(b))
}
} else {
fmt.Println("Database backups:")
for _, item := range list {
fmt.Println(item)
}
}
},
}
rootCmd.AddCommand(cmdDB)
cmdDB.AddCommand(cmdDBBackup, cmdDBList, cmdDBRestore)
cmdDBBackup.Flags().StringVarP(&tmpDBBackupName, "name", "n", "","Name of backup")
cmdDBRestore.Flags().StringVarP(&tmpDBBackupName, "name", "n", "","Name of backup")
}

View File

@ -10,13 +10,14 @@ import (
var (
StrRemoteHost string
StrRemotePort string
BoolJson bool
)
// rootCmd represents the base command when called without any subcommands
var rootCmd = &cobra.Command{
Use: "P4wnP1_cli",
Short: "P4wnP1 (remote) CLI configuration",
Long: `The cli_client tool could be used to configure P4wnP1
Long: `The CLI client tool could be used to configure P4wnP1
from the command line. The tool relies on RPC so it could be used
remotely.`,
}
@ -31,6 +32,7 @@ func Execute() {
func init() {
rootCmd.PersistentFlags().StringVar(&StrRemoteHost, "host", "localhost", "The host with the listening P4wnP1 RPC server")
rootCmd.PersistentFlags().StringVar(&StrRemotePort, "port", "50051", "The port on which the P4wnP1 RPC server is listening")
rootCmd.PersistentFlags().BoolVar(&BoolJson, "json", false, "Output results as JSON if applicable")
/*
// Cobra also supports local flags, which will only run

View File

@ -1,274 +1,193 @@
package cli_client
import (
"encoding/json"
"fmt"
"github.com/davecgh/go-spew/spew"
"github.com/spf13/cobra"
"google.golang.org/grpc/status"
"log"
"os"
pb "github.com/mame82/P4wnP1_go/proto"
"github.com/spf13/cobra"
"github.com/spf13/pflag"
"os"
)
type devPath int
const (
dev_path_hid_keyboard devPath = iota
dev_path_hid_mouse
dev_path_hid_raw
dev_path_hid_all
templateFlagNameBluetooth = "bluetooth"
templateFlagNameNetwork = "network"
templateFlagNameTriggerActions = "trigger-actions"
templateFlagNameWifi = "wifi"
templateFlagNameUsb = "usb"
templateFlagNameFullSettings = "full"
)
var templateFlagNames = map[string]bool{
templateFlagNameBluetooth: true,
templateFlagNameNetwork: true,
templateFlagNameTriggerActions: true,
templateFlagNameWifi: true,
templateFlagNameUsb: true,
templateFlagNameFullSettings: true,
}
var (
tmpUsbDisableGadget = false
tmpUsbUseHIDKeyboard = false
tmpUsbUseHIDMouse = false
tmpUsbUseHIDRaw = false
tmpUsbUseRNDIS = false
tmpUsbUseECM = false
tmpUsbUseSerial = false
tmpUsbUseUMS = false
tmpUsbUMSFile = ""
tmpUsbUMSCdromMode = false
// deploy
tmpTemplateTypeFullSettings = ""
tmpTemplateTypeNetwork = ""
tmpTemplateTypeWifi = ""
tmpTemplateTypeUsb = ""
tmpTemplateTypeBluetooth = ""
tmpTemplateTypeTriggerActions = ""
// tmpTemplateName = ""
//list
tmpTemplateTypeFullSettingsToggle = false
tmpTemplateTypeNetworkToggle = false
tmpTemplateTypeWifiToggle = false
tmpTemplateTypeUsbToggle = false
tmpTemplateTypeBluetoothToggle = false
tmpTemplateTypeTriggerActionsToggle = false
tmpUsbSerialnumber = "deadbeef1337"
tmpUsbVid = "0x1d6b"
tmpUsbPid = "0x1347"
tmpUsbManufacturer = "MaMe82"
tmpUsbProduct = "P4wnP1 by MaMe82"
)
func PrintGadgetSettings(gs *pb.GadgetSettings, useJson bool) {
res := ""
if useJson {
b, err := json.Marshal(gs)
if err == nil {
res = string(b)
}
} else {
// res = "Composite Gadget\n"
res += fmt.Sprintf("Enabled: %v\n", gs.Enabled)
res += fmt.Sprintf("Product: %s\n", gs.Product)
res += fmt.Sprintf("Manufacturer: %s\n", gs.Manufacturer)
res += fmt.Sprintf("Serialnumber: %s\n", gs.Serial)
res += fmt.Sprintf("PID: %s\n", gs.Pid)
res += fmt.Sprintf("VID: %s\n", gs.Vid)
res += "\n"
res += fmt.Sprintf("Functions:\n")
res += fmt.Sprintf(" RNDIS: %v\n", gs.Use_RNDIS)
res += fmt.Sprintf(" CDC ECM: %v\n", gs.Use_CDC_ECM)
res += fmt.Sprintf(" Serial: %v\n", gs.Use_SERIAL)
res += fmt.Sprintf(" HID Mouse: %v\n", gs.Use_HID_MOUSE)
res += fmt.Sprintf(" HID Keyboard: %v\n", gs.Use_HID_KEYBOARD)
res += fmt.Sprintf(" HID Generic: %v\n", gs.Use_HID_RAW)
res += fmt.Sprintf(" Mass Storage: %v\n", gs.Use_UMS)
if gs.Use_UMS {
if gs.UmsSettings.Cdrom {
res += fmt.Sprintf(" ---- Storage Mode: CD-Rom\n")
} else {
res += fmt.Sprintf(" ---- Storage Mode: Flashdrive\n")
}
res += fmt.Sprintf(" ---- Storage File: %s\n", gs.UmsSettings.File)
func listTemplateType(ttype pb.ActionDeploySettingsTemplate_TemplateType) (err error) {
fmt.Println("Templates of type", ttype, ":")
list,err := ClientListTemplateType(TIMEOUT_MEDIUM, StrRemoteHost, StrRemotePort, ttype)
if err != nil {
fmt.Println("Error retrieving templates: ", err.Error())
return err
}
for _,s := range list {
fmt.Println(s)
}
return nil
}
func deployTemplateType(ttype pb.ActionDeploySettingsTemplate_TemplateType, name string) (err error){
fmt.Print("Deploying template of type ", ttype, ", name '", name, "': ...")
err = ClientDeployTemplateType(TIMEOUT_MEDIUM, StrRemoteHost, StrRemotePort, ttype, name)
if err != nil {
fmt.Println("failed\n ", err.Error())
return err
}
fmt.Println("success")
return nil
}
func parseFlagsDeploy(cmd *cobra.Command) (res map[pb.ActionDeploySettingsTemplate_TemplateType]string) {
res = make(map[pb.ActionDeploySettingsTemplate_TemplateType]string)
cmd.Flags().Visit(func(flag *pflag.Flag) {
if _,exists := templateFlagNames[flag.Name]; exists {
switch flag.Name {
case templateFlagNameBluetooth:
res[pb.ActionDeploySettingsTemplate_BLUETOOTH] = flag.Value.String()
case templateFlagNameFullSettings:
res[pb.ActionDeploySettingsTemplate_FULL_SETTINGS] = flag.Value.String()
case templateFlagNameUsb:
res[pb.ActionDeploySettingsTemplate_USB] = flag.Value.String()
case templateFlagNameWifi:
res[pb.ActionDeploySettingsTemplate_WIFI] = flag.Value.String()
case templateFlagNameTriggerActions:
res[pb.ActionDeploySettingsTemplate_TRIGGER_ACTIONS] = flag.Value.String()
case templateFlagNameNetwork:
res[pb.ActionDeploySettingsTemplate_NETWORK] = flag.Value.String()
}
}
fmt.Println(res)
}
})
//fmt.Printf("%+v\n", res)
return res
}
func usbSet(cmd *cobra.Command, args []string) {
gs, err := ClientGetGadgetSettings(StrRemoteHost, StrRemotePort)
if err != nil {
log.Println(err)
return
}
gs.Pid = tmpUsbPid
gs.Vid = tmpUsbVid
gs.Product = tmpUsbProduct
gs.Manufacturer = tmpUsbManufacturer
gs.Serial = tmpUsbSerialnumber
gs.Enabled = !tmpUsbDisableGadget
gs.Use_RNDIS = tmpUsbUseRNDIS
gs.Use_CDC_ECM = tmpUsbUseECM
gs.Use_SERIAL = tmpUsbUseSerial
gs.Use_HID_KEYBOARD = tmpUsbUseHIDKeyboard
gs.Use_HID_MOUSE = tmpUsbUseHIDMouse
gs.Use_HID_RAW = tmpUsbUseHIDRaw
gs.Use_UMS = tmpUsbUseUMS
if tmpUsbUseUMS {
gs.UmsSettings.Cdrom = tmpUsbUMSCdromMode
if cmd.Flags().Lookup("ums-file").Changed {
fmt.Printf("Serving USB Mass Storage from '%s'\n", tmpUMSFile)
gs.UmsSettings.File = tmpUMSFile
func parseFlagsList(cmd *cobra.Command) (res []pb.ActionDeploySettingsTemplate_TemplateType) {
cmd.Flags().Visit(func(flag *pflag.Flag) {
if _,exists := templateFlagNames[flag.Name]; exists {
switch flag.Name {
case templateFlagNameBluetooth:
res = append(res, pb.ActionDeploySettingsTemplate_BLUETOOTH)
case templateFlagNameFullSettings:
res = append(res, pb.ActionDeploySettingsTemplate_FULL_SETTINGS)
case templateFlagNameUsb:
res = append(res, pb.ActionDeploySettingsTemplate_USB)
case templateFlagNameWifi:
res = append(res, pb.ActionDeploySettingsTemplate_WIFI)
case templateFlagNameTriggerActions:
res = append(res, pb.ActionDeploySettingsTemplate_TRIGGER_ACTIONS)
case templateFlagNameNetwork:
res = append(res, pb.ActionDeploySettingsTemplate_NETWORK)
}
}
})
if len(res) == 0 {
res = append(res,
pb.ActionDeploySettingsTemplate_FULL_SETTINGS,
pb.ActionDeploySettingsTemplate_BLUETOOTH,
pb.ActionDeploySettingsTemplate_USB,
pb.ActionDeploySettingsTemplate_WIFI,
pb.ActionDeploySettingsTemplate_TRIGGER_ACTIONS,
pb.ActionDeploySettingsTemplate_NETWORK,
)
}
//Update service settings
err = ClientSetGadgetSettings(StrRemoteHost, StrRemotePort, *gs)
if err != nil {
fmt.Printf("Error setting new gadget settings: %v\n", status.Convert(err).Message())
os.Exit(-1)
return
}
//deploy updated settings and fetch result (effectively deployed settings)
if gs, err := ClientDeployGadgetSettings(StrRemoteHost, StrRemotePort); err != nil {
fmt.Printf("Error deploying Gadget Settings: %v\nReverted to:\n%s", err, spew.Sdump(gs))
os.Exit(-1)
}
if BoolJson {
PrintGadgetSettings(gs,true)
} else {
fmt.Println("Successfully deployed USB gadget settings")
PrintGadgetSettings(gs,false)
}
return
}
func usbGetDevicePath(dev devPath) {
gs, err := ClientGetDeployedGadgetSettings(StrRemoteHost, StrRemotePort)
if err != nil {
fmt.Println("%+v\n", err)
os.Exit(-1)
}
res := struct {
DevPathKeyboard string
DevPathMouse string
DevPathRaw string
}{}
res.DevPathKeyboard = gs.DevPathHidKeyboard
res.DevPathMouse = gs.DevPathHidMouse
res.DevPathRaw = gs.DevPathHidRaw
if dev == dev_path_hid_raw && len(res.DevPathRaw) == 0 {
fmt.Println("Error: raw HID device disabled")
os.Exit(-1)
}
if dev == dev_path_hid_keyboard && len(res.DevPathKeyboard) == 0 {
fmt.Println("Error: HID keyboard device disabled")
os.Exit(-1)
}
if dev == dev_path_hid_mouse && len(res.DevPathMouse) == 0 {
fmt.Println("Error: HID mouse device disabled")
os.Exit(-1)
}
if BoolJson {
var bytes []byte
switch dev {
case dev_path_hid_keyboard:
bytes, err = json.Marshal(res.DevPathKeyboard)
case dev_path_hid_mouse:
bytes, err = json.Marshal(res.DevPathMouse)
case dev_path_hid_raw:
bytes, err = json.Marshal(res.DevPathRaw)
case dev_path_hid_all:
bytes, err = json.Marshal(res)
default:
bytes, err = json.Marshal(res)
}
if err != nil {
fmt.Println("Error: ", err)
os.Exit(-1)
}
fmt.Println(string(bytes))
} else {
switch dev {
case dev_path_hid_keyboard:
fmt.Println(res.DevPathKeyboard)
case dev_path_hid_mouse:
fmt.Println(res.DevPathMouse)
case dev_path_hid_raw:
fmt.Println(res.DevPathRaw)
case dev_path_hid_all:
fmt.Printf("%+v\n", res)
default:
fmt.Printf("%+v\n", res)
}
}
//fmt.Printf("%+v\n", res)
return res
}
func init() {
cmdUsb := &cobra.Command{
Use: "usb",
Short: "USB gadget settings",
cmdTemplate := &cobra.Command{
Use: "template",
Short: "Deploy and list templates",
}
cmdUsbDeploy := &cobra.Command{
cmdTemplateDeploy := &cobra.Command{
Use: "deploy",
Short: "Deploy given gadget settings",
Run: func(cmd *cobra.Command, args []string) {
deployList := parseFlagsDeploy(cmd)
for ttype,name := range deployList {
err := deployTemplateType(ttype,name)
if err != nil {
os.Exit(-1)
}
}
},
}
cmdUsbSet := &cobra.Command{
Use: "set",
Short: "set USB Gadget settings",
cmdTemplateList := &cobra.Command{
Use: "list",
Short: "List templates",
Long: ``,
Run: usbSet,
}
Run: func(cmd *cobra.Command, args []string) {
showList := parseFlagsList(cmd)
for _,ttype := range showList {
err := listTemplateType(ttype)
if err != nil {
os.Exit(-1)
}
}
cmdUsbGet := &cobra.Command{
Use: "get",
Short: "Retrieve information on current USB gadget settings",
}
cmdUsbGetDevice := &cobra.Command{
Use: "device",
Short: "Retrieve information on current USB gadget settings",
Run: func(cmd *cobra.Command, args []string) {
usbGetDevicePath(dev_path_hid_all)
},
}
cmdUsbGetDeviceKbd := &cobra.Command{
Use: "keyboard",
Short: "Retrieve path of HID keyboard device",
Run: func(cmd *cobra.Command, args []string) {
usbGetDevicePath(dev_path_hid_keyboard)
},
}
cmdUsbGetDeviceMouse := &cobra.Command{
Use: "mouse",
Short: "Retrieve path of HID mouse device",
Run: func(cmd *cobra.Command, args []string) {
usbGetDevicePath(dev_path_hid_mouse)
},
}
cmdUsbGetDeviceRaw := &cobra.Command{
Use: "raw",
Short: "Retrieve path of HID raw device",
Run: func(cmd *cobra.Command, args []string) {
usbGetDevicePath(dev_path_hid_raw)
},
}
rootCmd.AddCommand(cmdUsb)
cmdUsb.AddCommand(cmdUsbDeploy, cmdUsbSet, cmdUsbGet)
cmdUsbGet.AddCommand(cmdUsbGetDevice)
cmdUsbGetDevice.AddCommand(cmdUsbGetDeviceKbd)
cmdUsbGetDevice.AddCommand(cmdUsbGetDeviceMouse)
cmdUsbGetDevice.AddCommand(cmdUsbGetDeviceRaw)
cmdUsbSet.Flags().BoolVarP(&tmpUsbDisableGadget, "disable", "n", false, "If this flag is set, the gadget stays inactive after deployment (not bound to UDC)")
cmdUsbSet.Flags().BoolVarP(&tmpUsbUseRNDIS, "rndis", "r", false, "Use the RNDIS gadget function")
cmdUsbSet.Flags().BoolVarP(&tmpUsbUseECM, "cdc-ecm", "e", false, "Use the CDC ECM gadget function")
cmdUsbSet.Flags().BoolVarP(&tmpUsbUseSerial, "serial", "s", false, "Use the SERIAL gadget function")
cmdUsbSet.Flags().BoolVarP(&tmpUsbUseHIDKeyboard, "hid-keyboard", "k", false, "Use the HID KEYBOARD gadget function")
cmdUsbSet.Flags().BoolVarP(&tmpUsbUseHIDMouse, "hid-mouse", "m", false, "Use the HID MOUSE gadget function")
cmdUsbSet.Flags().BoolVarP(&tmpUsbUseHIDRaw, "hid-raw", "g", false, "Use the HID RAW gadget function")
cmdUsbSet.Flags().BoolVarP(&tmpUsbUseUMS, "ums", "u", false, "Use the USB Mass Storage gadget function")
cmdUsbSet.Flags().BoolVar(&tmpUsbUMSCdromMode, "ums-cdrom", false, "If this flag is set, UMS emulates a CD-Rom instead of a flashdrive (ignored, if UMS disabled)")
cmdUsbSet.Flags().StringVar(&tmpUsbUMSFile, "ums-file", "", "Path to the image or block device backing UMS (ignored, if UMS disabled)")
rootCmd.AddCommand(cmdTemplate)
cmdTemplate.AddCommand(cmdTemplateDeploy, cmdTemplateList)
cmdTemplateList.Flags().BoolVarP(&tmpTemplateTypeBluetoothToggle, templateFlagNameBluetooth, "b", false,"List existing bluetooth settings templates")
cmdTemplateList.Flags().BoolVarP(&tmpTemplateTypeNetworkToggle, templateFlagNameNetwork, "n", false,"List existing network settings templates")
cmdTemplateList.Flags().BoolVarP(&tmpTemplateTypeTriggerActionsToggle, templateFlagNameTriggerActions, "t", false,"List existing trigger action templates")
cmdTemplateList.Flags().BoolVarP(&tmpTemplateTypeWifiToggle, templateFlagNameWifi, "w", false,"List existing WiFi settings templates")
cmdTemplateList.Flags().BoolVarP(&tmpTemplateTypeUsbToggle, templateFlagNameUsb, "u", false,"List existing USB settings templates")
cmdTemplateList.Flags().BoolVarP(&tmpTemplateTypeFullSettingsToggle, templateFlagNameFullSettings, "f", false,"List existing full settings templates")
cmdTemplateDeploy.Flags().StringVarP(&tmpTemplateTypeBluetooth, templateFlagNameBluetooth, "b", "","Deploy Bluetooth template")
cmdTemplateDeploy.Flags().StringVarP(&tmpTemplateTypeNetwork, templateFlagNameNetwork, "n", "","Deploy network settings template")
cmdTemplateDeploy.Flags().StringVarP(&tmpTemplateTypeTriggerActions, templateFlagNameTriggerActions, "t", "","Deploy trigger action template")
cmdTemplateDeploy.Flags().StringVarP(&tmpTemplateTypeWifi, templateFlagNameWifi, "w", "","Deploy WiFi settings templates")
cmdTemplateDeploy.Flags().StringVarP(&tmpTemplateTypeUsb, templateFlagNameUsb, "u", "","Deploy USB settings template")
cmdTemplateDeploy.Flags().StringVarP(&tmpTemplateTypeFullSettings, templateFlagNameFullSettings, "f", "","Deploy full settings template")
cmdUsbSet.Flags().StringVarP(&tmpUsbSerialnumber, "sn", "x", "deadbeef1337", "Serial number (alpha numeric)")
cmdUsbSet.Flags().StringVarP(&tmpUsbVid, "vid", "v", "0x1d6b", "Vendor ID (format '0x1d6b')")
cmdUsbSet.Flags().StringVarP(&tmpUsbPid, "pid", "p", "0x1347", "Product ID (format '0x1347')")
cmdUsbSet.Flags().StringVarP(&tmpUsbManufacturer, "manufacturer", "f", "MaMe82", "Manufacturer string")
cmdUsbSet.Flags().StringVarP(&tmpUsbProduct, "product", "o", "P4wnP1 by MaMe82", "Product name string")
}

View File

@ -1 +1,274 @@
package cli_client
import (
"encoding/json"
"fmt"
"github.com/davecgh/go-spew/spew"
"github.com/spf13/cobra"
"google.golang.org/grpc/status"
"log"
"os"
pb "github.com/mame82/P4wnP1_go/proto"
)
type devPath int
const (
dev_path_hid_keyboard devPath = iota
dev_path_hid_mouse
dev_path_hid_raw
dev_path_hid_all
)
var (
tmpUsbDisableGadget = false
tmpUsbUseHIDKeyboard = false
tmpUsbUseHIDMouse = false
tmpUsbUseHIDRaw = false
tmpUsbUseRNDIS = false
tmpUsbUseECM = false
tmpUsbUseSerial = false
tmpUsbUseUMS = false
tmpUsbUMSFile = ""
tmpUsbUMSCdromMode = false
tmpUsbSerialnumber = "deadbeef1337"
tmpUsbVid = "0x1d6b"
tmpUsbPid = "0x1347"
tmpUsbManufacturer = "MaMe82"
tmpUsbProduct = "P4wnP1 by MaMe82"
)
func PrintGadgetSettings(gs *pb.GadgetSettings, useJson bool) {
res := ""
if useJson {
b, err := json.Marshal(gs)
if err == nil {
res = string(b)
}
} else {
// res = "Composite Gadget\n"
res += fmt.Sprintf("Enabled: %v\n", gs.Enabled)
res += fmt.Sprintf("Product: %s\n", gs.Product)
res += fmt.Sprintf("Manufacturer: %s\n", gs.Manufacturer)
res += fmt.Sprintf("Serialnumber: %s\n", gs.Serial)
res += fmt.Sprintf("PID: %s\n", gs.Pid)
res += fmt.Sprintf("VID: %s\n", gs.Vid)
res += "\n"
res += fmt.Sprintf("Functions:\n")
res += fmt.Sprintf(" RNDIS: %v\n", gs.Use_RNDIS)
res += fmt.Sprintf(" CDC ECM: %v\n", gs.Use_CDC_ECM)
res += fmt.Sprintf(" Serial: %v\n", gs.Use_SERIAL)
res += fmt.Sprintf(" HID Mouse: %v\n", gs.Use_HID_MOUSE)
res += fmt.Sprintf(" HID Keyboard: %v\n", gs.Use_HID_KEYBOARD)
res += fmt.Sprintf(" HID Generic: %v\n", gs.Use_HID_RAW)
res += fmt.Sprintf(" Mass Storage: %v\n", gs.Use_UMS)
if gs.Use_UMS {
if gs.UmsSettings.Cdrom {
res += fmt.Sprintf(" ---- Storage Mode: CD-Rom\n")
} else {
res += fmt.Sprintf(" ---- Storage Mode: Flashdrive\n")
}
res += fmt.Sprintf(" ---- Storage File: %s\n", gs.UmsSettings.File)
}
}
fmt.Println(res)
}
func usbSet(cmd *cobra.Command, args []string) {
gs, err := ClientGetGadgetSettings(StrRemoteHost, StrRemotePort)
if err != nil {
log.Println(err)
return
}
gs.Pid = tmpUsbPid
gs.Vid = tmpUsbVid
gs.Product = tmpUsbProduct
gs.Manufacturer = tmpUsbManufacturer
gs.Serial = tmpUsbSerialnumber
gs.Enabled = !tmpUsbDisableGadget
gs.Use_RNDIS = tmpUsbUseRNDIS
gs.Use_CDC_ECM = tmpUsbUseECM
gs.Use_SERIAL = tmpUsbUseSerial
gs.Use_HID_KEYBOARD = tmpUsbUseHIDKeyboard
gs.Use_HID_MOUSE = tmpUsbUseHIDMouse
gs.Use_HID_RAW = tmpUsbUseHIDRaw
gs.Use_UMS = tmpUsbUseUMS
if tmpUsbUseUMS {
gs.UmsSettings.Cdrom = tmpUsbUMSCdromMode
if cmd.Flags().Lookup("ums-file").Changed {
fmt.Printf("Serving USB Mass Storage from '%s'\n", tmpUMSFile)
gs.UmsSettings.File = tmpUMSFile
}
}
//Update service settings
err = ClientSetGadgetSettings(StrRemoteHost, StrRemotePort, *gs)
if err != nil {
fmt.Printf("Error setting new gadget settings: %v\n", status.Convert(err).Message())
os.Exit(-1)
return
}
//deploy updated settings and fetch result (effectively deployed settings)
if gs, err := ClientDeployGadgetSettings(StrRemoteHost, StrRemotePort); err != nil {
fmt.Printf("Error deploying Gadget Settings: %v\nReverted to:\n%s", err, spew.Sdump(gs))
os.Exit(-1)
}
if BoolJson {
PrintGadgetSettings(gs,true)
} else {
fmt.Println("Successfully deployed USB gadget settings")
PrintGadgetSettings(gs,false)
}
return
}
func usbGetDevicePath(dev devPath) {
gs, err := ClientGetDeployedGadgetSettings(StrRemoteHost, StrRemotePort)
if err != nil {
fmt.Println("%+v\n", err)
os.Exit(-1)
}
res := struct {
DevPathKeyboard string
DevPathMouse string
DevPathRaw string
}{}
res.DevPathKeyboard = gs.DevPathHidKeyboard
res.DevPathMouse = gs.DevPathHidMouse
res.DevPathRaw = gs.DevPathHidRaw
if dev == dev_path_hid_raw && len(res.DevPathRaw) == 0 {
fmt.Println("Error: raw HID device disabled")
os.Exit(-1)
}
if dev == dev_path_hid_keyboard && len(res.DevPathKeyboard) == 0 {
fmt.Println("Error: HID keyboard device disabled")
os.Exit(-1)
}
if dev == dev_path_hid_mouse && len(res.DevPathMouse) == 0 {
fmt.Println("Error: HID mouse device disabled")
os.Exit(-1)
}
if BoolJson {
var bytes []byte
switch dev {
case dev_path_hid_keyboard:
bytes, err = json.Marshal(res.DevPathKeyboard)
case dev_path_hid_mouse:
bytes, err = json.Marshal(res.DevPathMouse)
case dev_path_hid_raw:
bytes, err = json.Marshal(res.DevPathRaw)
case dev_path_hid_all:
bytes, err = json.Marshal(res)
default:
bytes, err = json.Marshal(res)
}
if err != nil {
fmt.Println("Error: ", err)
os.Exit(-1)
}
fmt.Println(string(bytes))
} else {
switch dev {
case dev_path_hid_keyboard:
fmt.Println(res.DevPathKeyboard)
case dev_path_hid_mouse:
fmt.Println(res.DevPathMouse)
case dev_path_hid_raw:
fmt.Println(res.DevPathRaw)
case dev_path_hid_all:
fmt.Printf("%+v\n", res)
default:
fmt.Printf("%+v\n", res)
}
}
}
func init() {
cmdUsb := &cobra.Command{
Use: "usb",
Short: "USB gadget settings",
}
cmdUsbDeploy := &cobra.Command{
Use: "deploy",
Short: "Deploy given gadget settings",
}
cmdUsbSet := &cobra.Command{
Use: "set",
Short: "set USB Gadget settings",
Long: ``,
Run: usbSet,
}
cmdUsbGet := &cobra.Command{
Use: "get",
Short: "Retrieve information on current USB gadget settings",
}
cmdUsbGetDevice := &cobra.Command{
Use: "device",
Short: "Retrieve information on current USB gadget settings",
Run: func(cmd *cobra.Command, args []string) {
usbGetDevicePath(dev_path_hid_all)
},
}
cmdUsbGetDeviceKbd := &cobra.Command{
Use: "keyboard",
Short: "Retrieve path of HID keyboard device",
Run: func(cmd *cobra.Command, args []string) {
usbGetDevicePath(dev_path_hid_keyboard)
},
}
cmdUsbGetDeviceMouse := &cobra.Command{
Use: "mouse",
Short: "Retrieve path of HID mouse device",
Run: func(cmd *cobra.Command, args []string) {
usbGetDevicePath(dev_path_hid_mouse)
},
}
cmdUsbGetDeviceRaw := &cobra.Command{
Use: "raw",
Short: "Retrieve path of HID raw device",
Run: func(cmd *cobra.Command, args []string) {
usbGetDevicePath(dev_path_hid_raw)
},
}
rootCmd.AddCommand(cmdUsb)
cmdUsb.AddCommand(cmdUsbDeploy, cmdUsbSet, cmdUsbGet)
cmdUsbGet.AddCommand(cmdUsbGetDevice)
cmdUsbGetDevice.AddCommand(cmdUsbGetDeviceKbd)
cmdUsbGetDevice.AddCommand(cmdUsbGetDeviceMouse)
cmdUsbGetDevice.AddCommand(cmdUsbGetDeviceRaw)
cmdUsbSet.Flags().BoolVarP(&tmpUsbDisableGadget, "disable", "n", false, "If this flag is set, the gadget stays inactive after deployment (not bound to UDC)")
cmdUsbSet.Flags().BoolVarP(&tmpUsbUseRNDIS, "rndis", "r", false, "Use the RNDIS gadget function")
cmdUsbSet.Flags().BoolVarP(&tmpUsbUseECM, "cdc-ecm", "e", false, "Use the CDC ECM gadget function")
cmdUsbSet.Flags().BoolVarP(&tmpUsbUseSerial, "serial", "s", false, "Use the SERIAL gadget function")
cmdUsbSet.Flags().BoolVarP(&tmpUsbUseHIDKeyboard, "hid-keyboard", "k", false, "Use the HID KEYBOARD gadget function")
cmdUsbSet.Flags().BoolVarP(&tmpUsbUseHIDMouse, "hid-mouse", "m", false, "Use the HID MOUSE gadget function")
cmdUsbSet.Flags().BoolVarP(&tmpUsbUseHIDRaw, "hid-raw", "g", false, "Use the HID RAW gadget function")
cmdUsbSet.Flags().BoolVarP(&tmpUsbUseUMS, "ums", "u", false, "Use the USB Mass Storage gadget function")
cmdUsbSet.Flags().BoolVar(&tmpUsbUMSCdromMode, "ums-cdrom", false, "If this flag is set, UMS emulates a CD-Rom instead of a flashdrive (ignored, if UMS disabled)")
cmdUsbSet.Flags().StringVar(&tmpUsbUMSFile, "ums-file", "", "Path to the image or block device backing UMS (ignored, if UMS disabled)")
cmdUsbSet.Flags().StringVarP(&tmpUsbSerialnumber, "sn", "x", "deadbeef1337", "Serial number (alpha numeric)")
cmdUsbSet.Flags().StringVarP(&tmpUsbVid, "vid", "v", "0x1d6b", "Vendor ID (format '0x1d6b')")
cmdUsbSet.Flags().StringVarP(&tmpUsbPid, "pid", "p", "0x1347", "Product ID (format '0x1347')")
cmdUsbSet.Flags().StringVarP(&tmpUsbManufacturer, "manufacturer", "f", "MaMe82", "Manufacturer string")
cmdUsbSet.Flags().StringVarP(&tmpUsbProduct, "product", "o", "P4wnP1 by MaMe82", "Product name string")
}

9
cli_client/globals.go Normal file
View File

@ -0,0 +1,9 @@
package cli_client
import "time"
const (
TIMEOUT_SHORT = time.Second * 5
TIMEOUT_MEDIUM = time.Second * 10
TIMEOUT_LONG = time.Second * 30
)

View File

@ -1,13 +1,13 @@
package cli_client
import (
"google.golang.org/grpc"
"log"
"fmt"
pb "github.com/mame82/P4wnP1_go/proto"
"github.com/pkg/errors"
"golang.org/x/net/context"
"google.golang.org/grpc"
"io"
"log"
"time"
)
@ -354,4 +354,138 @@ func ClientHIDGetScriptJobResult(host string, port string, jobID uint32) (script
scriptRes,err = rpcClient.HIDGetScriptJobResult(context.Background(), req)
return
}
}
func ClientListTemplateType(timeout time.Duration, host string, port string, ttype pb.ActionDeploySettingsTemplate_TemplateType) (res []string, err error) {
address := host + ":" + port
connection, err := grpc.Dial(address, grpc.WithInsecure())
if err != nil { log.Fatalf("Could not connect to P4wnP1 RPC server: %v", err) }
defer connection.Close()
rpcClient := pb.NewP4WNP1Client(connection)
ctx := context.Background()
if timeout > 0 {
ctxNew,cancel := context.WithTimeout(ctx, timeout)
ctx = ctxNew
defer cancel()
}
switch ttype {
case pb.ActionDeploySettingsTemplate_USB:
ma,err := rpcClient.ListStoredUSBSettings(ctx, &pb.Empty{})
if err != nil { return res,err }
return ma.MsgArray,nil
case pb.ActionDeploySettingsTemplate_TRIGGER_ACTIONS:
ma,err := rpcClient.ListStoredTriggerActionSets(ctx, &pb.Empty{})
if err != nil { return res,err }
return ma.MsgArray,nil
case pb.ActionDeploySettingsTemplate_WIFI:
ma,err := rpcClient.ListStoredWifiSettings(ctx, &pb.Empty{})
if err != nil { return res,err }
return ma.MsgArray,nil
case pb.ActionDeploySettingsTemplate_NETWORK:
ma,err := rpcClient.ListStoredEthernetInterfaceSettings(ctx, &pb.Empty{})
if err != nil { return res,err }
return ma.MsgArray,nil
case pb.ActionDeploySettingsTemplate_BLUETOOTH:
return
case pb.ActionDeploySettingsTemplate_FULL_SETTINGS:
return
default:
return res,errors.New("unknown template type")
}
}
func ClientDeployTemplateType(timeout time.Duration, host string, port string, ttype pb.ActionDeploySettingsTemplate_TemplateType, name string) (err error) {
address := host + ":" + port
connection, err := grpc.Dial(address, grpc.WithInsecure())
if err != nil { log.Fatalf("Could not connect to P4wnP1 RPC server: %v", err) }
defer connection.Close()
rpcClient := pb.NewP4WNP1Client(connection)
ctx := context.Background()
if timeout > 0 {
ctxNew,cancel := context.WithTimeout(ctx, timeout)
ctx = ctxNew
defer cancel()
}
switch ttype {
case pb.ActionDeploySettingsTemplate_USB:
_,err = rpcClient.DeployStoredUSBSettings(ctx, &pb.StringMessage{Msg:name})
case pb.ActionDeploySettingsTemplate_TRIGGER_ACTIONS:
_,err = rpcClient.DeployStoredTriggerActionSetReplace(ctx, &pb.StringMessage{Msg:name})
case pb.ActionDeploySettingsTemplate_WIFI:
_,err = rpcClient.DeployStoredWifiSettings(ctx, &pb.StringMessage{Msg:name})
case pb.ActionDeploySettingsTemplate_NETWORK:
_,err = rpcClient.DeployStoredEthernetInterfaceSettings(ctx, &pb.StringMessage{Msg:name})
case pb.ActionDeploySettingsTemplate_BLUETOOTH:
return
case pb.ActionDeploySettingsTemplate_FULL_SETTINGS:
return
default:
return errors.New("unknown template type")
}
return
}
func ClientDBBackup(timeout time.Duration, host string, port string, name string) (err error) {
address := host + ":" + port
connection, err := grpc.Dial(address, grpc.WithInsecure())
if err != nil { log.Fatalf("Could not connect to P4wnP1 RPC server: %v", err) }
defer connection.Close()
rpcClient := pb.NewP4WNP1Client(connection)
ctx := context.Background()
if timeout > 0 {
ctxNew,cancel := context.WithTimeout(ctx, timeout)
ctx = ctxNew
defer cancel()
}
_,err = rpcClient.DBBackup(ctx, &pb.StringMessage{Msg:name})
return
}
func ClientDBRestore(timeout time.Duration, host string, port string, name string) (err error) {
address := host + ":" + port
connection, err := grpc.Dial(address, grpc.WithInsecure())
if err != nil { log.Fatalf("Could not connect to P4wnP1 RPC server: %v", err) }
defer connection.Close()
rpcClient := pb.NewP4WNP1Client(connection)
ctx := context.Background()
if timeout > 0 {
ctxNew,cancel := context.WithTimeout(ctx, timeout)
ctx = ctxNew
defer cancel()
}
_,err = rpcClient.DBRestore(ctx, &pb.StringMessage{Msg:name})
return
}
func ClientDBList(timeout time.Duration, host string, port string) (names []string, err error) {
address := host + ":" + port
connection, err := grpc.Dial(address, grpc.WithInsecure())
if err != nil { log.Fatalf("Could not connect to P4wnP1 RPC server: %v", err) }
defer connection.Close()
rpcClient := pb.NewP4WNP1Client(connection)
ctx := context.Background()
if timeout > 0 {
ctxNew,cancel := context.WithTimeout(ctx, timeout)
ctx = ctxNew
defer cancel()
}
backups,err := rpcClient.ListStoredDBBackups(ctx, &pb.Empty{})
if err != nil { return names, err}
return backups.MsgArray,nil
}

0
dist/db/.gitkeep vendored Normal file
View File

View File

@ -6181,8 +6181,12 @@ type P4WNP1Client interface {
StoreTriggerActionSet(ctx context.Context, in *TriggerActionSet, opts ...grpcweb.CallOption) (*Empty, error)
DeployStoredTriggerActionSetReplace(ctx context.Context, in *StringMessage, opts ...grpcweb.CallOption) (*TriggerActionSet, error)
DeployStoredTriggerActionSetAdd(ctx context.Context, in *StringMessage, opts ...grpcweb.CallOption) (*TriggerActionSet, error)
// DB backup&restore
DBBackup(ctx context.Context, in *StringMessage, opts ...grpcweb.CallOption) (*Empty, error)
DBRestore(ctx context.Context, in *StringMessage, opts ...grpcweb.CallOption) (*Empty, error)
ListStoredHIDScripts(ctx context.Context, in *Empty, opts ...grpcweb.CallOption) (*StringMessageArray, error)
ListStoredBashScripts(ctx context.Context, in *Empty, opts ...grpcweb.CallOption) (*StringMessageArray, error)
ListStoredDBBackups(ctx context.Context, in *Empty, opts ...grpcweb.CallOption) (*StringMessageArray, error)
}
type p4WNP1Client struct {
@ -6696,6 +6700,24 @@ func (c *p4WNP1Client) DeployStoredTriggerActionSetAdd(ctx context.Context, in *
return new(TriggerActionSet).Unmarshal(resp)
}
func (c *p4WNP1Client) DBBackup(ctx context.Context, in *StringMessage, opts ...grpcweb.CallOption) (*Empty, error) {
resp, err := c.client.RPCCall(ctx, "DBBackup", in.Marshal(), opts...)
if err != nil {
return nil, err
}
return new(Empty).Unmarshal(resp)
}
func (c *p4WNP1Client) DBRestore(ctx context.Context, in *StringMessage, opts ...grpcweb.CallOption) (*Empty, error) {
resp, err := c.client.RPCCall(ctx, "DBRestore", in.Marshal(), opts...)
if err != nil {
return nil, err
}
return new(Empty).Unmarshal(resp)
}
func (c *p4WNP1Client) ListStoredHIDScripts(ctx context.Context, in *Empty, opts ...grpcweb.CallOption) (*StringMessageArray, error) {
resp, err := c.client.RPCCall(ctx, "ListStoredHIDScripts", in.Marshal(), opts...)
if err != nil {
@ -6713,3 +6735,12 @@ func (c *p4WNP1Client) ListStoredBashScripts(ctx context.Context, in *Empty, opt
return new(StringMessageArray).Unmarshal(resp)
}
func (c *p4WNP1Client) ListStoredDBBackups(ctx context.Context, in *Empty, opts ...grpcweb.CallOption) (*StringMessageArray, error) {
resp, err := c.client.RPCCall(ctx, "ListStoredDBBackups", in.Marshal(), opts...)
if err != nil {
return nil, err
}
return new(StringMessageArray).Unmarshal(resp)
}

View File

@ -3009,8 +3009,12 @@ type P4WNP1Client interface {
StoreTriggerActionSet(ctx context.Context, in *TriggerActionSet, opts ...grpc.CallOption) (*Empty, error)
DeployStoredTriggerActionSetReplace(ctx context.Context, in *StringMessage, opts ...grpc.CallOption) (*TriggerActionSet, error)
DeployStoredTriggerActionSetAdd(ctx context.Context, in *StringMessage, opts ...grpc.CallOption) (*TriggerActionSet, error)
// DB backup&restore
DBBackup(ctx context.Context, in *StringMessage, opts ...grpc.CallOption) (*Empty, error)
DBRestore(ctx context.Context, in *StringMessage, opts ...grpc.CallOption) (*Empty, error)
ListStoredHIDScripts(ctx context.Context, in *Empty, opts ...grpc.CallOption) (*StringMessageArray, error)
ListStoredBashScripts(ctx context.Context, in *Empty, opts ...grpc.CallOption) (*StringMessageArray, error)
ListStoredDBBackups(ctx context.Context, in *Empty, opts ...grpc.CallOption) (*StringMessageArray, error)
}
type p4WNP1Client struct {
@ -3521,6 +3525,24 @@ func (c *p4WNP1Client) DeployStoredTriggerActionSetAdd(ctx context.Context, in *
return out, nil
}
func (c *p4WNP1Client) DBBackup(ctx context.Context, in *StringMessage, opts ...grpc.CallOption) (*Empty, error) {
out := new(Empty)
err := grpc.Invoke(ctx, "/P4wnP1_grpc.P4WNP1/DBBackup", in, out, c.cc, opts...)
if err != nil {
return nil, err
}
return out, nil
}
func (c *p4WNP1Client) DBRestore(ctx context.Context, in *StringMessage, opts ...grpc.CallOption) (*Empty, error) {
out := new(Empty)
err := grpc.Invoke(ctx, "/P4wnP1_grpc.P4WNP1/DBRestore", in, out, c.cc, opts...)
if err != nil {
return nil, err
}
return out, nil
}
func (c *p4WNP1Client) ListStoredHIDScripts(ctx context.Context, in *Empty, opts ...grpc.CallOption) (*StringMessageArray, error) {
out := new(StringMessageArray)
err := grpc.Invoke(ctx, "/P4wnP1_grpc.P4WNP1/ListStoredHIDScripts", in, out, c.cc, opts...)
@ -3539,6 +3561,15 @@ func (c *p4WNP1Client) ListStoredBashScripts(ctx context.Context, in *Empty, opt
return out, nil
}
func (c *p4WNP1Client) ListStoredDBBackups(ctx context.Context, in *Empty, opts ...grpc.CallOption) (*StringMessageArray, error) {
out := new(StringMessageArray)
err := grpc.Invoke(ctx, "/P4wnP1_grpc.P4WNP1/ListStoredDBBackups", in, out, c.cc, opts...)
if err != nil {
return nil, err
}
return out, nil
}
// Server API for P4WNP1 service
type P4WNP1Server interface {
@ -3604,8 +3635,12 @@ type P4WNP1Server interface {
StoreTriggerActionSet(context.Context, *TriggerActionSet) (*Empty, error)
DeployStoredTriggerActionSetReplace(context.Context, *StringMessage) (*TriggerActionSet, error)
DeployStoredTriggerActionSetAdd(context.Context, *StringMessage) (*TriggerActionSet, error)
// DB backup&restore
DBBackup(context.Context, *StringMessage) (*Empty, error)
DBRestore(context.Context, *StringMessage) (*Empty, error)
ListStoredHIDScripts(context.Context, *Empty) (*StringMessageArray, error)
ListStoredBashScripts(context.Context, *Empty) (*StringMessageArray, error)
ListStoredDBBackups(context.Context, *Empty) (*StringMessageArray, error)
}
func RegisterP4WNP1Server(s *grpc.Server, srv P4WNP1Server) {
@ -4569,6 +4604,42 @@ func _P4WNP1_DeployStoredTriggerActionSetAdd_Handler(srv interface{}, ctx contex
return interceptor(ctx, in, info, handler)
}
func _P4WNP1_DBBackup_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) {
in := new(StringMessage)
if err := dec(in); err != nil {
return nil, err
}
if interceptor == nil {
return srv.(P4WNP1Server).DBBackup(ctx, in)
}
info := &grpc.UnaryServerInfo{
Server: srv,
FullMethod: "/P4wnP1_grpc.P4WNP1/DBBackup",
}
handler := func(ctx context.Context, req interface{}) (interface{}, error) {
return srv.(P4WNP1Server).DBBackup(ctx, req.(*StringMessage))
}
return interceptor(ctx, in, info, handler)
}
func _P4WNP1_DBRestore_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) {
in := new(StringMessage)
if err := dec(in); err != nil {
return nil, err
}
if interceptor == nil {
return srv.(P4WNP1Server).DBRestore(ctx, in)
}
info := &grpc.UnaryServerInfo{
Server: srv,
FullMethod: "/P4wnP1_grpc.P4WNP1/DBRestore",
}
handler := func(ctx context.Context, req interface{}) (interface{}, error) {
return srv.(P4WNP1Server).DBRestore(ctx, req.(*StringMessage))
}
return interceptor(ctx, in, info, handler)
}
func _P4WNP1_ListStoredHIDScripts_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) {
in := new(Empty)
if err := dec(in); err != nil {
@ -4605,6 +4676,24 @@ func _P4WNP1_ListStoredBashScripts_Handler(srv interface{}, ctx context.Context,
return interceptor(ctx, in, info, handler)
}
func _P4WNP1_ListStoredDBBackups_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) {
in := new(Empty)
if err := dec(in); err != nil {
return nil, err
}
if interceptor == nil {
return srv.(P4WNP1Server).ListStoredDBBackups(ctx, in)
}
info := &grpc.UnaryServerInfo{
Server: srv,
FullMethod: "/P4wnP1_grpc.P4WNP1/ListStoredDBBackups",
}
handler := func(ctx context.Context, req interface{}) (interface{}, error) {
return srv.(P4WNP1Server).ListStoredDBBackups(ctx, req.(*Empty))
}
return interceptor(ctx, in, info, handler)
}
var _P4WNP1_serviceDesc = grpc.ServiceDesc{
ServiceName: "P4wnP1_grpc.P4WNP1",
HandlerType: (*P4WNP1Server)(nil),
@ -4817,6 +4906,14 @@ var _P4WNP1_serviceDesc = grpc.ServiceDesc{
MethodName: "DeployStoredTriggerActionSetAdd",
Handler: _P4WNP1_DeployStoredTriggerActionSetAdd_Handler,
},
{
MethodName: "DBBackup",
Handler: _P4WNP1_DBBackup_Handler,
},
{
MethodName: "DBRestore",
Handler: _P4WNP1_DBRestore_Handler,
},
{
MethodName: "ListStoredHIDScripts",
Handler: _P4WNP1_ListStoredHIDScripts_Handler,
@ -4825,6 +4922,10 @@ var _P4WNP1_serviceDesc = grpc.ServiceDesc{
MethodName: "ListStoredBashScripts",
Handler: _P4WNP1_ListStoredBashScripts_Handler,
},
{
MethodName: "ListStoredDBBackups",
Handler: _P4WNP1_ListStoredDBBackups_Handler,
},
},
Streams: []grpc.StreamDesc{
{
@ -4839,288 +4940,290 @@ var _P4WNP1_serviceDesc = grpc.ServiceDesc{
func init() { proto.RegisterFile("grpc.proto", fileDescriptor0) }
var fileDescriptor0 = []byte{
// 4524 bytes of a gzipped FileDescriptorProto
// 4553 bytes of a gzipped FileDescriptorProto
0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0xb4, 0x5b, 0x4b, 0x77, 0x1b, 0x47,
0x76, 0x06, 0x08, 0x3e, 0x80, 0x0b, 0x80, 0x6c, 0x96, 0x48, 0x0a, 0xa2, 0x5e, 0x56, 0x5b, 0xf6,
0x68, 0xe8, 0x98, 0xb6, 0x69, 0x59, 0x7e, 0xc4, 0x8e, 0x07, 0x2f, 0x02, 0x90, 0x40, 0x00, 0xa9,
0x06, 0xc4, 0x99, 0x4c, 0xce, 0xf4, 0x34, 0xba, 0x8b, 0x60, 0x5b, 0x40, 0x37, 0xd2, 0x0f, 0xd2,
0xcc, 0x62, 0x72, 0xce, 0xac, 0xb2, 0xc8, 0x3e, 0xff, 0x22, 0xbb, 0x24, 0x7f, 0x22, 0x7f, 0x24,
0x9b, 0x39, 0xd9, 0x64, 0x93, 0x4d, 0x72, 0xaa, 0xaa, 0xdf, 0x68, 0x90, 0x94, 0x94, 0xd9, 0x55,
0xdd, 0xba, 0xf5, 0x55, 0xd5, 0x7d, 0xd5, 0xad, 0xdb, 0x00, 0xc0, 0xc4, 0x9a, 0xab, 0x87, 0x73,
0xcb, 0x74, 0x4c, 0x54, 0x1c, 0x3c, 0xbf, 0x34, 0x06, 0x5f, 0xc8, 0x94, 0x24, 0x1e, 0xc0, 0x5e,
0x6d, 0xea, 0x12, 0xc7, 0x34, 0x9d, 0xf3, 0xea, 0x84, 0x18, 0x8e, 0x44, 0x1c, 0x47, 0x37, 0x26,
0x36, 0x12, 0x20, 0x37, 0xd7, 0x8d, 0x4a, 0xf6, 0x83, 0xec, 0xb3, 0x02, 0xa6, 0x4d, 0xf1, 0x7f,
0xb2, 0x70, 0x37, 0x60, 0xee, 0x11, 0xe7, 0xd2, 0xb4, 0xde, 0x48, 0xc4, 0xba, 0xd0, 0x55, 0x82,
0x9e, 0xc3, 0x9e, 0x45, 0x26, 0xba, 0xed, 0x10, 0x4b, 0x36, 0x2d, 0xd9, 0x35, 0xfc, 0x1e, 0x03,
0xc8, 0xe3, 0x1d, 0xbf, 0xdf, 0xb7, 0x46, 0xc1, 0x18, 0x3a, 0x80, 0x6d, 0x9b, 0x58, 0x17, 0x7c,
0x8e, 0x6a, 0x1a, 0x06, 0x51, 0x9d, 0xca, 0x0a, 0x9b, 0xb0, 0xc5, 0x07, 0xfa, 0x56, 0x9d, 0x93,
0xd1, 0xf7, 0xb0, 0xea, 0x5c, 0xcd, 0x49, 0x25, 0xf7, 0x41, 0xf6, 0xd9, 0xe6, 0xd1, 0xb3, 0xc3,
0xc8, 0x29, 0x0e, 0x97, 0xec, 0x6a, 0x78, 0x35, 0x27, 0x98, 0xcd, 0x42, 0x8f, 0xa0, 0x38, 0x53,
0x54, 0xba, 0x8c, 0xa1, 0xcc, 0x48, 0x65, 0x95, 0x9d, 0xaa, 0x30, 0x53, 0xd4, 0xbe, 0xd5, 0x53,
0x66, 0x04, 0x3d, 0x86, 0xe2, 0xd8, 0xd2, 0xb5, 0x09, 0xe1, 0xe3, 0x6b, 0x6c, 0x1c, 0x38, 0x89,
0x32, 0x88, 0xff, 0xb9, 0x0a, 0xf7, 0x83, 0x65, 0xea, 0xa6, 0xe1, 0x58, 0xe6, 0x74, 0x4a, 0xac,
0x40, 0x5c, 0x15, 0xd8, 0x98, 0x9b, 0x97, 0xc4, 0x22, 0x9a, 0x77, 0x62, 0xbf, 0x8b, 0x3e, 0x80,
0xa2, 0x77, 0x34, 0x65, 0x3c, 0x25, 0xde, 0xf1, 0xa2, 0x24, 0xf4, 0x4b, 0x10, 0xce, 0x14, 0xdb,
0x91, 0xa3, 0x6c, 0x39, 0x2e, 0x05, 0x4a, 0xaf, 0x47, 0x58, 0x45, 0x28, 0x69, 0xba, 0xad, 0x9a,
0x17, 0xc4, 0x62, 0x6c, 0xab, 0x8c, 0x2d, 0x46, 0x43, 0xfb, 0x90, 0x1f, 0x9b, 0x86, 0xc6, 0xc6,
0xd7, 0xd8, 0x78, 0xd0, 0x47, 0x87, 0x70, 0x67, 0xaa, 0x1b, 0x6f, 0xe4, 0x29, 0xb9, 0x20, 0x53,
0xd9, 0x26, 0xaa, 0x6b, 0xe9, 0xce, 0x55, 0x65, 0x9d, 0xb1, 0x6d, 0xd3, 0xa1, 0x2e, 0x1d, 0x91,
0xbc, 0x01, 0x74, 0x04, 0xbb, 0x8c, 0x89, 0xc8, 0xb6, 0x3e, 0x9b, 0x4f, 0x89, 0x3c, 0x57, 0x74,
0x4b, 0x37, 0x26, 0x95, 0x0d, 0x36, 0xe3, 0x0e, 0x1f, 0x94, 0xd8, 0xd8, 0x80, 0x0f, 0xa1, 0x5d,
0x58, 0x1f, 0x5b, 0x32, 0xd1, 0xac, 0x4a, 0x9e, 0x31, 0xad, 0x8d, 0xad, 0xa6, 0x66, 0xa1, 0x87,
0x00, 0xe7, 0xfa, 0xe4, 0x5c, 0xb6, 0xe7, 0x84, 0x68, 0x95, 0x02, 0x1b, 0x2a, 0x50, 0x8a, 0x44,
0x09, 0x74, 0x78, 0x6a, 0x5e, 0xca, 0xc4, 0x20, 0xd6, 0xe4, 0xaa, 0x02, 0x7c, 0x78, 0x6a, 0x5e,
0x36, 0x19, 0x81, 0x4a, 0x51, 0xd1, 0x2e, 0x88, 0xe5, 0xe8, 0x36, 0x5d, 0xbe, 0xc8, 0xa5, 0x18,
0x21, 0xa1, 0x4f, 0x01, 0x79, 0x5b, 0xf5, 0xe4, 0xa8, 0x9b, 0x86, 0x5d, 0x29, 0xf1, 0x93, 0xf1,
0x91, 0x7a, 0x38, 0x40, 0xd7, 0xd3, 0xc8, 0xd8, 0x9d, 0xc8, 0x6f, 0xc8, 0x95, 0x5d, 0x29, 0xf3,
0xf5, 0x18, 0xe5, 0x15, 0xb9, 0xe2, 0xfa, 0xb4, 0xf4, 0x0b, 0x45, 0xbd, 0xaa, 0x6c, 0x7a, 0xfa,
0xe4, 0x5d, 0xf4, 0x2d, 0x54, 0xd4, 0x40, 0xff, 0x74, 0xad, 0x33, 0x7d, 0xe2, 0x5a, 0x0a, 0x45,
0xad, 0x6c, 0x31, 0xd6, 0xbb, 0xe1, 0x78, 0x3d, 0x3a, 0x8c, 0x3e, 0x82, 0x4d, 0xdb, 0x51, 0x1c,
0x5d, 0x95, 0x15, 0x4d, 0xb3, 0x88, 0x6d, 0x57, 0x04, 0x36, 0xa1, 0xcc, 0xa9, 0x55, 0x4e, 0x14,
0xff, 0xb4, 0x0a, 0x8f, 0x52, 0x6c, 0xad, 0x63, 0x9c, 0x99, 0xd6, 0x8c, 0x23, 0x55, 0x60, 0xc3,
0x87, 0xa0, 0xe6, 0x56, 0xc2, 0x7e, 0x17, 0x7d, 0x02, 0xdb, 0x63, 0x7f, 0xae, 0x7c, 0x41, 0x2c,
0x9b, 0xee, 0x8b, 0x1a, 0x5d, 0x19, 0x0b, 0xc1, 0xc0, 0x6b, 0x4e, 0xa7, 0xe6, 0x34, 0x53, 0x0c,
0xf7, 0x4c, 0x51, 0x1d, 0xd7, 0x22, 0x16, 0xb3, 0xba, 0x32, 0x8e, 0xd1, 0xd0, 0x29, 0x20, 0xdb,
0x9d, 0xcf, 0x4d, 0xcb, 0x21, 0x9a, 0x6c, 0x7b, 0xf6, 0xce, 0x0c, 0xaf, 0xb8, 0xcc, 0x0d, 0x17,
0xfd, 0x03, 0x6f, 0x07, 0x18, 0x81, 0xcb, 0x48, 0x20, 0xa8, 0xae, 0x65, 0x11, 0xc3, 0x09, 0x61,
0xd7, 0xde, 0x12, 0x76, 0xcb, 0x43, 0x08, 0x40, 0x3f, 0x86, 0x2d, 0x75, 0xaa, 0xd8, 0xb6, 0x6c,
0x9e, 0xc9, 0x1a, 0xa1, 0x51, 0x80, 0x19, 0x77, 0x09, 0x97, 0x19, 0xb9, 0x7f, 0xd6, 0x60, 0x44,
0x84, 0x60, 0x95, 0x79, 0xfa, 0x06, 0xf3, 0x74, 0xd6, 0xa6, 0x26, 0x61, 0x9f, 0x9b, 0x96, 0xc3,
0x63, 0x40, 0x9e, 0xc7, 0x08, 0x46, 0x61, 0x31, 0xe2, 0x09, 0x94, 0x74, 0x5b, 0x56, 0x2e, 0x14,
0x7d, 0xca, 0x7c, 0x8b, 0x9b, 0x70, 0x51, 0xb7, 0xab, 0x3e, 0x09, 0xfd, 0x25, 0xec, 0xdb, 0x3c,
0xf6, 0xc8, 0x06, 0x0f, 0x45, 0xb2, 0x17, 0xe0, 0x0c, 0x65, 0xee, 0x19, 0xf5, 0x5d, 0x8f, 0x23,
0x12, 0xab, 0x88, 0xd5, 0x53, 0xe6, 0xe8, 0x07, 0xb8, 0xbf, 0x64, 0xf2, 0x5c, 0x31, 0x5c, 0xcf,
0xe4, 0x2b, 0x69, 0xb3, 0x07, 0x8a, 0xe1, 0xa2, 0x6f, 0xe1, 0xde, 0x92, 0xe9, 0x13, 0xc3, 0x73,
0x83, 0xbd, 0xb4, 0xc9, 0x2d, 0x43, 0xfc, 0x09, 0x84, 0xa1, 0xa5, 0x4f, 0x26, 0xc4, 0xaa, 0x32,
0xef, 0x90, 0x88, 0x83, 0x6a, 0xb0, 0x19, 0xa3, 0x51, 0x43, 0xcb, 0x3d, 0x2b, 0x1e, 0xed, 0xc7,
0x74, 0x13, 0x63, 0xc1, 0x89, 0x19, 0x54, 0xc8, 0x54, 0x72, 0xcc, 0xfc, 0x0a, 0x98, 0xb5, 0xc5,
0x7f, 0x03, 0x28, 0xc7, 0xd8, 0xd0, 0x26, 0xac, 0xe8, 0x3c, 0x6a, 0x96, 0xf1, 0x8a, 0xae, 0x51,
0xdb, 0x36, 0x0d, 0x22, 0x9d, 0x9b, 0xfe, 0x5d, 0xe0, 0x77, 0x69, 0x64, 0xd3, 0x6d, 0x3a, 0xeb,
0xc2, 0x0f, 0x90, 0x41, 0x1f, 0x3d, 0x80, 0x82, 0x3e, 0x9b, 0xb9, 0x4e, 0x24, 0x2c, 0x86, 0x04,
0xd4, 0x85, 0x4d, 0xef, 0xec, 0x92, 0xa3, 0x50, 0x2b, 0xf4, 0x2c, 0x4d, 0x4c, 0x3b, 0x8d, 0x14,
0xe3, 0x6c, 0x67, 0x70, 0x62, 0x2e, 0xfa, 0x35, 0x20, 0xd7, 0x1e, 0xb7, 0x14, 0x6d, 0x42, 0xfc,
0xe8, 0x4c, 0x34, 0x66, 0x67, 0xc5, 0xa3, 0x8f, 0xd3, 0x10, 0x47, 0x52, 0x2d, 0xc1, 0xdd, 0xce,
0xe0, 0x14, 0x0c, 0xa4, 0xc0, 0x6e, 0x40, 0x6d, 0xd0, 0xa0, 0xee, 0x83, 0x6f, 0x30, 0xf0, 0x5f,
0x5e, 0x0b, 0x1e, 0x9d, 0xd0, 0xce, 0xe0, 0x74, 0x24, 0xd4, 0x81, 0xf2, 0xa5, 0x7e, 0xa6, 0x57,
0x07, 0xbe, 0x24, 0xf2, 0x0c, 0xfa, 0x49, 0x1a, 0xf4, 0x69, 0x94, 0xb1, 0x9d, 0xc1, 0xf1, 0x99,
0x54, 0x0e, 0x94, 0x10, 0x6c, 0xbf, 0x6a, 0x4b, 0x8e, 0xc2, 0xfc, 0x62, 0x89, 0x1c, 0x4e, 0x17,
0xb8, 0xa9, 0x1c, 0x16, 0x31, 0xd0, 0x77, 0x90, 0xb7, 0xed, 0xf3, 0xae, 0x39, 0xd1, 0x0d, 0xe6,
0x36, 0xc5, 0xa3, 0x07, 0xa9, 0x9a, 0x92, 0xda, 0x8c, 0xa7, 0x9d, 0xc1, 0x01, 0x3f, 0xc2, 0x20,
0x68, 0xe7, 0xea, 0xbc, 0x4b, 0x14, 0x9b, 0xb4, 0x2c, 0xc5, 0xa0, 0x67, 0x2c, 0x32, 0x8c, 0xa7,
0x69, 0x18, 0x8d, 0x76, 0x7d, 0x10, 0xe5, 0x6d, 0x67, 0xf0, 0xc2, 0x7c, 0x74, 0x0c, 0xa5, 0x89,
0x65, 0xba, 0x73, 0x4c, 0x54, 0x42, 0xad, 0xaf, 0xc4, 0xf0, 0x3e, 0x48, 0xc3, 0x6b, 0x45, 0xf8,
0xda, 0x19, 0x1c, 0x9b, 0x87, 0x7e, 0x07, 0x3b, 0xd1, 0xbe, 0x44, 0xfe, 0xce, 0x25, 0x86, 0x4a,
0xd8, 0xfd, 0x93, 0x8c, 0x7b, 0x29, 0x78, 0x3e, 0x7f, 0x3b, 0x83, 0x53, 0x71, 0xd0, 0x73, 0x58,
0x9f, 0xcc, 0x75, 0xb3, 0x63, 0xb0, 0x5b, 0x6b, 0x89, 0xb7, 0xb6, 0x06, 0x9d, 0x7e, 0x87, 0xca,
0xcc, 0xe3, 0x45, 0x0d, 0x80, 0xb1, 0x62, 0x9f, 0x4b, 0xaa, 0xa5, 0xcf, 0x1d, 0x76, 0x89, 0x25,
0x3d, 0xc3, 0x8b, 0x0b, 0x54, 0xef, 0xb5, 0x80, 0xb3, 0x9d, 0xc5, 0x91, 0x79, 0xa8, 0x0a, 0x85,
0x73, 0x5d, 0xf3, 0x40, 0x84, 0x14, 0xa3, 0x8a, 0x80, 0xb4, 0x3b, 0x8d, 0x00, 0x23, 0x9c, 0x85,
0x54, 0xd8, 0xd3, 0xc8, 0x7c, 0x6a, 0x5e, 0xf9, 0xf1, 0x7c, 0x48, 0x66, 0xf3, 0xa9, 0xe2, 0x90,
0xca, 0x76, 0x8a, 0xfd, 0x73, 0xbc, 0x46, 0xea, 0x84, 0x76, 0x16, 0x2f, 0x81, 0x42, 0x07, 0x90,
0x9b, 0x9a, 0x93, 0x0a, 0x62, 0x88, 0x7b, 0x29, 0x88, 0x5d, 0x73, 0xd2, 0xce, 0x62, 0xca, 0x84,
0x5e, 0xc0, 0x06, 0x95, 0x51, 0xdf, 0x75, 0x2a, 0x77, 0x52, 0x04, 0xca, 0xf9, 0xa9, 0x3c, 0xfb,
0x2e, 0x3d, 0x8a, 0xcf, 0x8c, 0xbe, 0x87, 0x02, 0xd3, 0x8f, 0x44, 0x0c, 0xad, 0xb2, 0x93, 0x62,
0xc0, 0xde, 0x4c, 0x9f, 0x87, 0x8a, 0x21, 0x98, 0x50, 0x2b, 0xc0, 0x86, 0xa7, 0xaa, 0x5a, 0x1e,
0xd6, 0x39, 0xab, 0x78, 0x17, 0x76, 0x53, 0xe3, 0x93, 0x78, 0x1f, 0xee, 0x2d, 0x0d, 0x33, 0xe2,
0x23, 0x78, 0x70, 0x5d, 0x98, 0x10, 0xf7, 0x60, 0x27, 0xcd, 0xd7, 0x23, 0xa0, 0x8b, 0x3e, 0x2b,
0x7e, 0x06, 0x5b, 0x09, 0x07, 0xa4, 0xe1, 0x77, 0x4a, 0x1b, 0x23, 0xdb, 0xcb, 0xf9, 0x0b, 0x38,
0x24, 0x88, 0xf7, 0xe0, 0xee, 0x12, 0x6f, 0x13, 0x3b, 0x70, 0x27, 0xc5, 0xd0, 0x29, 0x1e, 0x93,
0x07, 0xbb, 0x3f, 0x3c, 0xbc, 0x80, 0x80, 0x76, 0x60, 0xed, 0x42, 0x99, 0xba, 0xfc, 0x66, 0x59,
0xc3, 0xbc, 0x23, 0xfe, 0x03, 0xdc, 0xbf, 0xc6, 0x67, 0x6e, 0x80, 0x3c, 0x00, 0xa1, 0x33, 0x31,
0x4c, 0x8b, 0xf4, 0x5d, 0xa7, 0x7f, 0xd6, 0xb7, 0x34, 0x62, 0x79, 0xd7, 0xcf, 0x02, 0x1d, 0xed,
0xc1, 0x3a, 0x5b, 0xd1, 0xae, 0xe4, 0x3e, 0xc8, 0x3d, 0x5b, 0xc3, 0x5e, 0x4f, 0xfc, 0xf7, 0x6c,
0x70, 0xb7, 0x71, 0x1f, 0x43, 0x87, 0xdc, 0x7e, 0x7a, 0xee, 0x8c, 0xad, 0xb8, 0x79, 0xb4, 0x13,
0xb3, 0x02, 0xca, 0xd5, 0x73, 0x67, 0xd8, 0x67, 0x42, 0x3f, 0x00, 0xcc, 0xdd, 0xe9, 0x74, 0x34,
0x6f, 0x98, 0x97, 0x3c, 0x6d, 0xdb, 0x3c, 0x7a, 0xb8, 0x30, 0xa5, 0x63, 0x0c, 0x02, 0x26, 0x1c,
0x99, 0x80, 0xbe, 0x06, 0xe0, 0x2e, 0xdd, 0xd4, 0x26, 0xfe, 0x53, 0xe9, 0x6e, 0xca, 0x74, 0x3a,
0x8c, 0x23, 0xac, 0xe2, 0xd7, 0xb0, 0x9b, 0xea, 0xe2, 0xe8, 0x11, 0x80, 0xcd, 0x5a, 0x11, 0xa9,
0x45, 0x28, 0xe2, 0x0b, 0xd8, 0x49, 0x73, 0xeb, 0x1b, 0xe7, 0xfd, 0x77, 0x16, 0x1e, 0x5c, 0xe7,
0xbf, 0x34, 0x35, 0x75, 0xbc, 0x76, 0x04, 0x22, 0x46, 0x43, 0x2f, 0xbd, 0x37, 0x21, 0x97, 0xd3,
0x8b, 0x5b, 0x07, 0x87, 0x43, 0xbf, 0x11, 0xbe, 0x10, 0x45, 0x02, 0xa5, 0x28, 0x15, 0x6d, 0x43,
0xf9, 0x78, 0xd4, 0xed, 0xca, 0x52, 0x73, 0x38, 0xec, 0xf4, 0x5a, 0x92, 0x90, 0x41, 0x45, 0xd8,
0xe8, 0x35, 0x87, 0xa7, 0x7d, 0xfc, 0x4a, 0xc8, 0xa2, 0x3c, 0xac, 0x9e, 0x76, 0x8e, 0x3b, 0xc2,
0x0a, 0xda, 0x80, 0xdc, 0x48, 0xaa, 0x09, 0x39, 0x54, 0x86, 0x42, 0xad, 0x3b, 0x6a, 0x0e, 0xfb,
0xfd, 0x61, 0x5b, 0x58, 0x45, 0x77, 0x60, 0x6b, 0x88, 0x3b, 0xad, 0x56, 0x13, 0xcb, 0xd5, 0xfa,
0xb0, 0xd3, 0xef, 0x49, 0xc2, 0x9a, 0x58, 0x84, 0x42, 0x10, 0x64, 0xc4, 0x39, 0x94, 0x63, 0x11,
0xe4, 0xad, 0xcd, 0xe5, 0xb3, 0xa8, 0x1f, 0x6c, 0x1e, 0xdd, 0x5b, 0xe0, 0xee, 0xbb, 0xce, 0x6b,
0xca, 0xe0, 0xbb, 0x48, 0x13, 0xb6, 0x12, 0x91, 0xe7, 0x9d, 0x3c, 0xed, 0x12, 0xf6, 0x69, 0x58,
0xc0, 0xd4, 0xb5, 0xec, 0x20, 0xf9, 0x96, 0x1c, 0xd3, 0x52, 0x26, 0x4c, 0x75, 0xc3, 0x14, 0xd5,
0x45, 0x69, 0xe8, 0x2b, 0xc8, 0x07, 0x49, 0xff, 0x0a, 0x8b, 0x8f, 0xf1, 0xcd, 0x9f, 0xea, 0xc7,
0x7a, 0x90, 0xe5, 0x07, 0xac, 0xe2, 0x3f, 0xe7, 0xa0, 0x14, 0x1d, 0x0a, 0xf2, 0xf8, 0x6c, 0x24,
0x8f, 0xdf, 0x87, 0xbc, 0xa6, 0xdb, 0x34, 0xef, 0xd3, 0x3c, 0x17, 0x0e, 0xfa, 0xd4, 0x2e, 0x2d,
0x32, 0x71, 0xa7, 0x8a, 0x63, 0x5a, 0x57, 0xcc, 0x43, 0x0a, 0x38, 0x42, 0x41, 0x3f, 0x42, 0x89,
0xa6, 0xc6, 0xba, 0x31, 0x91, 0x67, 0xa6, 0xc6, 0x33, 0xc9, 0xcd, 0x44, 0xec, 0xa6, 0x1b, 0x38,
0xe5, 0x4c, 0x27, 0xa6, 0x46, 0x70, 0xf1, 0x32, 0xec, 0xa0, 0x17, 0x50, 0x50, 0x5c, 0xe7, 0x9c,
0xcf, 0x5e, 0x4b, 0x51, 0x0b, 0x9d, 0x5d, 0x75, 0x9d, 0x73, 0x36, 0x35, 0xaf, 0x78, 0x2d, 0x9a,
0xf5, 0xaa, 0xe7, 0x8a, 0x61, 0x90, 0x29, 0x4b, 0x24, 0xcb, 0xd8, 0xef, 0xa2, 0x43, 0x58, 0x57,
0xe6, 0x72, 0x4d, 0x92, 0xbc, 0x24, 0xf0, 0xee, 0x02, 0x5c, 0x4d, 0x92, 0xea, 0x67, 0x13, 0xbc,
0xa6, 0xcc, 0x6b, 0x92, 0x84, 0x7e, 0xa4, 0x4f, 0x20, 0x9d, 0x3e, 0xab, 0x6a, 0x92, 0x24, 0x4f,
0x75, 0xdb, 0xa9, 0xe4, 0x59, 0xea, 0xbe, 0x74, 0x62, 0x99, 0xf3, 0xd7, 0x24, 0xa9, 0xab, 0xdb,
0x0e, 0xba, 0xcf, 0x2e, 0x72, 0x22, 0xdb, 0xb6, 0xee, 0x3f, 0xd4, 0xf3, 0x94, 0x20, 0xd9, 0xba,
0x46, 0x63, 0x9f, 0x41, 0x7e, 0x9e, 0x99, 0x86, 0xf7, 0x66, 0xf6, 0x7a, 0xe2, 0xbf, 0x64, 0xa1,
0xc0, 0x34, 0xe3, 0x50, 0xef, 0x3d, 0x84, 0x55, 0x26, 0x00, 0x6e, 0xc5, 0xfb, 0x8b, 0xaa, 0xa5,
0x5c, 0x4c, 0x02, 0x8c, 0x2f, 0x7a, 0xfa, 0x95, 0xf8, 0xe9, 0x11, 0xac, 0xb2, 0x7d, 0x70, 0x55,
0xb1, 0x36, 0xaa, 0x43, 0xf2, 0xdd, 0xe7, 0xbd, 0x47, 0xaf, 0xb1, 0xa1, 0xe4, 0x0c, 0xf1, 0x08,
0x20, 0x14, 0x01, 0x5d, 0x46, 0x92, 0x3a, 0x0d, 0xdf, 0x8e, 0x68, 0x1b, 0x09, 0x90, 0x1b, 0x48,
0xaf, 0xbc, 0xd7, 0x0b, 0x6d, 0x8a, 0x4f, 0xa0, 0x2c, 0x39, 0x16, 0x55, 0x35, 0xb1, 0x6d, 0x6a,
0xea, 0x02, 0xe4, 0x66, 0xf6, 0xc4, 0xaf, 0x92, 0xcd, 0xec, 0x89, 0xf8, 0x39, 0xa0, 0x18, 0x4b,
0xd5, 0xb2, 0x94, 0x2b, 0x6a, 0x92, 0x33, 0x7b, 0xc2, 0xda, 0xec, 0x1d, 0x55, 0xc0, 0x41, 0x5f,
0x3c, 0x84, 0x52, 0xf3, 0x82, 0x18, 0x8e, 0xe7, 0x4d, 0xd4, 0x44, 0xa9, 0xd2, 0x88, 0x41, 0xe3,
0x10, 0x83, 0xce, 0xe1, 0x08, 0x45, 0x54, 0x00, 0x18, 0x3f, 0x73, 0x6c, 0xb4, 0x0f, 0x1b, 0x8e,
0xcd, 0x16, 0xe4, 0xbb, 0x68, 0x67, 0xb0, 0x4f, 0x40, 0x7b, 0xb0, 0xe6, 0x8c, 0x4d, 0x93, 0xcb,
0x34, 0xdf, 0xce, 0x60, 0xde, 0x45, 0x15, 0x58, 0x77, 0x74, 0xc3, 0x79, 0xf1, 0x9c, 0x49, 0x35,
0x47, 0x33, 0x41, 0xde, 0xaf, 0xad, 0x41, 0xee, 0x42, 0x99, 0x8a, 0x5d, 0x58, 0x63, 0x4b, 0x50,
0xb1, 0x38, 0xe1, 0x2e, 0x78, 0x2d, 0xed, 0xb3, 0xe0, 0xf6, 0x5b, 0x49, 0x31, 0xab, 0x70, 0x6b,
0xc1, 0xb5, 0xf8, 0x7b, 0xd8, 0xa1, 0xbe, 0xdf, 0xd0, 0xad, 0xbe, 0x75, 0xac, 0x4f, 0x89, 0x7f,
0x50, 0x01, 0x72, 0x9a, 0xee, 0x67, 0x0b, 0xb4, 0x49, 0x8d, 0x6b, 0x6e, 0x91, 0x33, 0xfd, 0x67,
0x4f, 0xe8, 0x5e, 0x8f, 0x8a, 0xc4, 0x34, 0xa6, 0x57, 0xc7, 0xe6, 0x54, 0xf3, 0xaa, 0x14, 0x79,
0x1c, 0xa1, 0xd0, 0xeb, 0x2b, 0xb1, 0x82, 0x3d, 0x37, 0x0d, 0x9b, 0x70, 0x77, 0xb7, 0xdd, 0xa9,
0x33, 0x50, 0x9c, 0x73, 0xff, 0x1a, 0x0a, 0x29, 0xe2, 0x3f, 0x65, 0x61, 0x0b, 0x13, 0x45, 0x8b,
0x6e, 0xeb, 0x2b, 0x58, 0x3f, 0xe3, 0x0b, 0x65, 0x53, 0xee, 0xdf, 0xaa, 0xaa, 0x12, 0xdb, 0xd6,
0xc7, 0x53, 0xc2, 0xd7, 0xc6, 0x1e, 0x33, 0x55, 0xf1, 0x99, 0x3e, 0x25, 0x46, 0xf8, 0xe0, 0x0d,
0xfa, 0x34, 0x8a, 0xda, 0xf4, 0x7e, 0xe4, 0xf2, 0xc6, 0xbc, 0x43, 0xcf, 0x3f, 0x25, 0x06, 0x33,
0xdd, 0x1c, 0xa6, 0x4d, 0xb1, 0x01, 0x42, 0xb8, 0x1b, 0xef, 0x08, 0x0f, 0xa0, 0x60, 0x11, 0x45,
0xab, 0x9b, 0xae, 0xe1, 0x78, 0x7a, 0x08, 0x09, 0x54, 0x41, 0x9a, 0xe2, 0x28, 0x6c, 0xc5, 0x12,
0x66, 0x6d, 0xf1, 0x5f, 0xb3, 0x20, 0x9c, 0x5a, 0xba, 0x43, 0xfe, 0xcc, 0xa7, 0xda, 0xa3, 0x81,
0x69, 0x4e, 0x33, 0x5c, 0xae, 0x11, 0xaf, 0xc7, 0xaa, 0x4a, 0xae, 0xed, 0xf4, 0x4c, 0xa7, 0xf9,
0x33, 0x8d, 0x3e, 0x5e, 0x91, 0x32, 0x4a, 0x0b, 0xf6, 0xbd, 0x16, 0xd9, 0xf7, 0x47, 0xb0, 0x45,
0x77, 0xdc, 0x31, 0xce, 0x4c, 0x7f, 0xd7, 0x08, 0x56, 0xe7, 0xa1, 0xe6, 0x58, 0x5b, 0xfc, 0x03,
0x08, 0x21, 0x9b, 0x27, 0xa4, 0xb4, 0x6b, 0x80, 0x46, 0x0e, 0xfd, 0xef, 0xf9, 0xb6, 0x73, 0x98,
0xb5, 0x29, 0x8d, 0xc5, 0x25, 0x5e, 0xe8, 0x0a, 0x62, 0xcf, 0xcc, 0xd4, 0x86, 0xba, 0x57, 0x17,
0xce, 0x61, 0xbf, 0x4b, 0xd5, 0xa6, 0xdb, 0x0d, 0xdd, 0xf2, 0xca, 0xa8, 0xbc, 0x23, 0xfe, 0x0d,
0x08, 0x41, 0x9e, 0x13, 0xf1, 0x59, 0x9e, 0xdc, 0x44, 0xed, 0x2c, 0xa4, 0xa0, 0x8f, 0x61, 0xd3,
0xd1, 0x67, 0xc4, 0x74, 0x1d, 0x89, 0xa8, 0xa6, 0xa1, 0xd9, 0x5e, 0x98, 0x4b, 0x50, 0xc5, 0x47,
0x50, 0x0a, 0xb0, 0x5f, 0x9a, 0xe3, 0x64, 0x6d, 0x44, 0x7c, 0x1a, 0x59, 0xfb, 0xa5, 0x39, 0x66,
0xe1, 0x5a, 0x80, 0x9c, 0xae, 0xf1, 0xf2, 0x4c, 0x19, 0xd3, 0xa6, 0xf8, 0x1a, 0x2a, 0xed, 0x4e,
0x03, 0xbb, 0x86, 0xa1, 0x1b, 0x93, 0x97, 0xe6, 0x98, 0x45, 0x5b, 0xcc, 0xac, 0x3e, 0x82, 0x98,
0x63, 0xd5, 0x16, 0x04, 0xab, 0x17, 0xb3, 0x8e, 0xe6, 0x4b, 0x89, 0xb6, 0xa9, 0x62, 0x6d, 0xd3,
0xb5, 0x54, 0xe2, 0x45, 0x5d, 0xaf, 0x27, 0xfe, 0x01, 0xb6, 0x22, 0x27, 0x67, 0x70, 0x9f, 0x40,
0xee, 0x27, 0x73, 0xcc, 0xf0, 0x92, 0xe1, 0x37, 0xba, 0x51, 0x4c, 0xb9, 0xa8, 0x94, 0x74, 0xfb,
0x58, 0x37, 0x74, 0xfb, 0x3c, 0xb8, 0x9a, 0x23, 0x94, 0xd0, 0x5b, 0x5f, 0xda, 0xa6, 0x11, 0x5e,
0xce, 0x3e, 0x45, 0x3c, 0x84, 0x62, 0xb7, 0xd9, 0x08, 0xee, 0xfe, 0xc7, 0x50, 0x1c, 0xb3, 0x6a,
0xb6, 0x1a, 0xf8, 0x46, 0x19, 0x03, 0x23, 0x31, 0xe7, 0x10, 0x7f, 0x86, 0x7b, 0x23, 0xa9, 0xf6,
0x1e, 0x59, 0xca, 0xd7, 0x0b, 0x59, 0xca, 0xfd, 0x78, 0x8a, 0xc5, 0x1e, 0x54, 0x29, 0x79, 0xca,
0x9f, 0xd6, 0x60, 0x33, 0x3e, 0x48, 0xcd, 0x8c, 0x18, 0x3c, 0x29, 0xf1, 0xbe, 0x10, 0x78, 0x5d,
0xaa, 0xc0, 0x0b, 0x5d, 0xf3, 0xef, 0x99, 0x0b, 0x5d, 0xe3, 0x1f, 0x5f, 0xfc, 0x3b, 0x8f, 0x36,
0x17, 0x2a, 0xb5, 0xfc, 0x0b, 0x46, 0xbc, 0x52, 0xcb, 0x6a, 0xd6, 0xa6, 0xe6, 0xaa, 0x8e, 0xf7,
0x01, 0xc3, 0xef, 0x32, 0x85, 0x12, 0x4b, 0x57, 0x78, 0x6e, 0x41, 0x15, 0xca, 0x7a, 0xe8, 0x11,
0x14, 0x5d, 0x9b, 0xc8, 0xf5, 0x46, 0x5d, 0x6e, 0xd6, 0x4f, 0xbc, 0xa2, 0x7e, 0xc1, 0xb5, 0x49,
0xbd, 0x51, 0x6f, 0xd6, 0x4f, 0x68, 0x26, 0x40, 0xc7, 0x71, 0xaf, 0xd1, 0x91, 0xbc, 0x6a, 0x7e,
0xde, 0xb5, 0x09, 0xeb, 0xa3, 0x67, 0x20, 0xd0, 0xc1, 0x76, 0xa7, 0x21, 0xbf, 0x6a, 0xfe, 0xa6,
0xd6, 0xaf, 0xe2, 0x86, 0x97, 0x2d, 0x6c, 0xba, 0x36, 0x69, 0x77, 0x1a, 0x3e, 0x15, 0x89, 0x50,
0xf6, 0x39, 0x4f, 0xfa, 0x23, 0xa9, 0xe9, 0x55, 0x42, 0x8b, 0x9c, 0x8d, 0x91, 0xfc, 0xad, 0x50,
0x1e, 0x5c, 0x3d, 0xf5, 0xaa, 0x9d, 0x05, 0xce, 0x81, 0xab, 0xa7, 0xe8, 0x2e, 0x6c, 0xd0, 0xf1,
0xd1, 0x89, 0xe4, 0x15, 0x33, 0xd7, 0x5d, 0x9b, 0x8c, 0x4e, 0x24, 0xf4, 0x10, 0x80, 0x0e, 0x48,
0x4d, 0xdc, 0xa9, 0x76, 0xfd, 0x42, 0xbe, 0x6b, 0x13, 0x4e, 0x40, 0x2f, 0x61, 0xd3, 0x32, 0x34,
0xdd, 0x0e, 0x6b, 0xcc, 0xbc, 0x32, 0xf2, 0xe1, 0x35, 0x8a, 0x6c, 0x3a, 0xe7, 0xc4, 0x32, 0x88,
0x83, 0xcb, 0x6c, 0x6a, 0xa0, 0xc2, 0x13, 0x10, 0x54, 0x4d, 0x95, 0x89, 0x3a, 0x0b, 0xd1, 0xb6,
0x6e, 0x8f, 0xb6, 0xa9, 0x6a, 0x6a, 0x53, 0x9d, 0x05, 0x70, 0x55, 0x28, 0xb9, 0xb3, 0xc8, 0xc6,
0x78, 0xcd, 0xe4, 0xd1, 0x35, 0x50, 0xa3, 0x13, 0x09, 0x17, 0xdd, 0x59, 0xb8, 0xa3, 0x2f, 0x60,
0x57, 0x23, 0x17, 0x32, 0x8d, 0x8b, 0xf2, 0xb9, 0xae, 0xc9, 0x6f, 0xc8, 0xd5, 0xd8, 0x54, 0x2c,
0x8d, 0x55, 0x37, 0x0a, 0x18, 0x69, 0xe4, 0x82, 0xc6, 0x9f, 0xb6, 0xae, 0xbd, 0xf2, 0x46, 0xd0,
0x27, 0x80, 0x62, 0x53, 0x66, 0xa6, 0x6b, 0x13, 0x56, 0xdd, 0x28, 0xe0, 0xad, 0x90, 0xff, 0x84,
0x92, 0xd1, 0x2f, 0x40, 0x88, 0x31, 0x5b, 0xca, 0x25, 0x2b, 0x67, 0x14, 0x70, 0x39, 0x64, 0xc5,
0xca, 0xa5, 0x38, 0x80, 0xbd, 0xf4, 0x53, 0xb3, 0x6c, 0xd2, 0xb4, 0x1d, 0xf6, 0xc9, 0xc3, 0x73,
0xb2, 0x3c, 0x25, 0x54, 0x35, 0xcd, 0x42, 0xf7, 0x20, 0x4f, 0xf1, 0xd9, 0x18, 0xb7, 0xff, 0x0d,
0x8d, 0x5c, 0xd0, 0x21, 0xf1, 0x07, 0xd8, 0x5e, 0x38, 0x3c, 0x8d, 0xc8, 0xaa, 0x66, 0x99, 0x33,
0xcf, 0x85, 0x78, 0x87, 0xc6, 0x30, 0x7a, 0x29, 0xf9, 0x75, 0x66, 0xda, 0x16, 0xff, 0x31, 0x0b,
0x8f, 0x02, 0xc9, 0xbf, 0x7b, 0x04, 0xa8, 0x2d, 0x44, 0x80, 0x78, 0x61, 0xd3, 0x5f, 0xa2, 0x63,
0x38, 0xc4, 0x3a, 0x53, 0x54, 0x92, 0x12, 0x0c, 0x64, 0x78, 0xc2, 0xdf, 0xa1, 0x44, 0x5b, 0xca,
0x8e, 0xbe, 0x83, 0x55, 0x96, 0xaa, 0xf3, 0x2a, 0xfb, 0x6d, 0x17, 0x61, 0x73, 0xc4, 0x3f, 0xe6,
0xe0, 0xde, 0x72, 0xe4, 0xb4, 0xbb, 0xf1, 0x47, 0xef, 0x1e, 0xe4, 0xef, 0xc6, 0x4f, 0x6e, 0xb7,
0xda, 0x61, 0x24, 0x61, 0xa7, 0xa1, 0x7c, 0xee, 0x7d, 0xb0, 0x7a, 0xee, 0x87, 0xea, 0x90, 0x42,
0xf3, 0x06, 0x83, 0x38, 0x33, 0xc5, 0x7e, 0xf3, 0xdc, 0x8b, 0x55, 0x41, 0x3f, 0x1a, 0x09, 0xd7,
0xe2, 0x91, 0xb0, 0x0f, 0x48, 0x3b, 0x57, 0xe7, 0xfc, 0xc3, 0x44, 0x90, 0xdb, 0xf3, 0xc2, 0xfa,
0xe3, 0xd8, 0x26, 0x1b, 0xed, 0xfa, 0x20, 0xce, 0x86, 0x53, 0xa6, 0xa2, 0xa7, 0x50, 0xf6, 0xd5,
0xd0, 0x31, 0x46, 0x36, 0xf1, 0x42, 0x5c, 0x9c, 0x28, 0xd6, 0x61, 0x95, 0xbd, 0xc1, 0x00, 0xd6,
0x4f, 0xaa, 0xbd, 0x51, 0xb5, 0x2b, 0x64, 0xd0, 0x16, 0x14, 0xe9, 0x1a, 0x72, 0xbd, 0xdb, 0x69,
0xf6, 0x86, 0x42, 0x36, 0x20, 0x48, 0x4d, 0xfc, 0xba, 0x89, 0x85, 0x15, 0xfa, 0xdc, 0x1f, 0xf5,
0x4e, 0xaa, 0xbd, 0x6a, 0xab, 0xd9, 0x10, 0x72, 0xe2, 0xff, 0xe6, 0x00, 0x2d, 0xee, 0x2a, 0xcc,
0xe6, 0x07, 0xa6, 0x15, 0xdc, 0x51, 0x21, 0x05, 0x3d, 0x83, 0x2d, 0xde, 0x0b, 0xc4, 0xed, 0x99,
0x71, 0x92, 0xcc, 0x4a, 0x6c, 0x44, 0xb1, 0x59, 0x56, 0xe7, 0x49, 0x3c, 0x24, 0xa0, 0x03, 0x10,
0x0c, 0xd3, 0xa1, 0x0f, 0x4b, 0xd3, 0xd2, 0x1d, 0x85, 0x7d, 0x23, 0xe1, 0x89, 0xd7, 0x02, 0x1d,
0x1d, 0x02, 0xd2, 0xcc, 0x9e, 0xe9, 0xd4, 0x74, 0x43, 0x0b, 0x97, 0xe5, 0xba, 0x48, 0x19, 0xa1,
0xd9, 0x8b, 0xaa, 0x4c, 0xa7, 0x63, 0x45, 0x7d, 0xe3, 0x95, 0x77, 0xf9, 0x35, 0x92, 0xa0, 0xa2,
0xe7, 0xb0, 0x6e, 0x29, 0xc6, 0x84, 0xd8, 0x95, 0x0d, 0x66, 0xc5, 0x0f, 0x96, 0xa8, 0x0c, 0x53,
0x26, 0xec, 0xf1, 0xa2, 0x63, 0xd8, 0x30, 0xe7, 0xfc, 0x13, 0x13, 0x7f, 0xa7, 0xfe, 0xc5, 0x0d,
0x9a, 0x3e, 0xec, 0x73, 0xf6, 0xa6, 0xe1, 0x58, 0x57, 0xd8, 0x9f, 0x8c, 0xea, 0x50, 0xe4, 0xdf,
0x51, 0xdb, 0xa6, 0xed, 0xd8, 0x95, 0x02, 0xc3, 0x7a, 0xb2, 0x0c, 0x2b, 0xe0, 0xc4, 0xd1, 0x59,
0xfb, 0xdf, 0x41, 0x29, 0x8a, 0x4e, 0x6f, 0xe2, 0x37, 0xe4, 0xca, 0xd3, 0x1b, 0x6d, 0xc6, 0x2b,
0x22, 0x05, 0xaf, 0x22, 0xf2, 0xdd, 0xca, 0x37, 0x59, 0xd1, 0x84, 0xad, 0xc4, 0x19, 0x59, 0x46,
0x43, 0x1b, 0x5d, 0xf3, 0x32, 0xa8, 0x8b, 0x46, 0x28, 0xc1, 0xf8, 0x68, 0x3e, 0x27, 0x7e, 0x04,
0x8c, 0x50, 0x02, 0x9d, 0xb3, 0xec, 0x34, 0xaa, 0x73, 0x4a, 0x10, 0xbf, 0x81, 0x9d, 0xb4, 0x13,
0xb1, 0x57, 0xa9, 0xa2, 0x06, 0xaf, 0x52, 0x45, 0x65, 0x59, 0xdf, 0xdc, 0xc3, 0x5f, 0xd1, 0xe7,
0xe2, 0x06, 0xac, 0x35, 0x67, 0x73, 0xe7, 0xea, 0xe0, 0x9b, 0xc8, 0xcf, 0x1a, 0x16, 0x7f, 0x3d,
0x81, 0x36, 0x20, 0xd7, 0xab, 0x0e, 0x84, 0x0c, 0xca, 0xc3, 0xea, 0xa0, 0xda, 0x1b, 0x09, 0x59,
0xb4, 0x0e, 0x2b, 0xad, 0x9e, 0xb0, 0x72, 0xf0, 0x29, 0x08, 0xc9, 0x5a, 0x24, 0x1d, 0x1b, 0x79,
0xdc, 0x8d, 0xfe, 0x69, 0x4f, 0xc8, 0x52, 0x80, 0xfe, 0xf1, 0xb1, 0xb0, 0x72, 0xf0, 0x19, 0x40,
0x58, 0x7b, 0xa4, 0x9e, 0x86, 0x3b, 0x52, 0xa7, 0xd7, 0xe2, 0x65, 0xb5, 0xe3, 0x6a, 0xb7, 0x4b,
0x3b, 0xac, 0xac, 0x56, 0xeb, 0x0f, 0xdb, 0xc2, 0xca, 0xc1, 0x7f, 0x65, 0x61, 0xc3, 0x2b, 0x78,
0xa1, 0x02, 0xac, 0xf5, 0x46, 0x27, 0xf2, 0x17, 0x42, 0xc6, 0x6f, 0x1e, 0x09, 0x59, 0xbf, 0xf9,
0xa5, 0xb0, 0xe2, 0x37, 0x9f, 0x0b, 0x39, 0xbf, 0xf9, 0x95, 0xb0, 0xea, 0x37, 0x5f, 0x08, 0x6b,
0x7e, 0xf3, 0x6b, 0x61, 0xdd, 0x6f, 0x7e, 0x23, 0x6c, 0xf8, 0xcd, 0x6f, 0x85, 0x3c, 0xdd, 0x11,
0x5b, 0xe2, 0x73, 0xa1, 0x10, 0xb4, 0xbf, 0x10, 0x20, 0x68, 0x1f, 0x09, 0xc5, 0xa0, 0xfd, 0xa5,
0x50, 0x0a, 0xda, 0xcf, 0x85, 0x72, 0xd0, 0xfe, 0x4a, 0xd8, 0x0c, 0xda, 0x2f, 0x84, 0xad, 0xa0,
0xfd, 0xb5, 0x20, 0x04, 0xed, 0x6f, 0x84, 0xed, 0xa0, 0xfd, 0xad, 0x80, 0xfc, 0xf6, 0xd1, 0xe7,
0xc2, 0x9d, 0x83, 0x4f, 0xa1, 0x14, 0x2d, 0xda, 0x51, 0xe1, 0x75, 0xfb, 0xa7, 0x5c, 0x9e, 0xed,
0x4e, 0xab, 0x2d, 0x64, 0x29, 0xfb, 0xb0, 0xdf, 0x6a, 0x75, 0x9b, 0xc2, 0xca, 0x41, 0x03, 0xb6,
0x12, 0xa5, 0x28, 0x2a, 0xcb, 0x51, 0xef, 0x55, 0x8f, 0xca, 0x3e, 0x43, 0xb5, 0x51, 0x1d, 0x70,
0x1d, 0x48, 0xc3, 0xaa, 0xb0, 0x82, 0xee, 0xc0, 0x96, 0x34, 0xac, 0xca, 0xc7, 0xd5, 0x4e, 0xb7,
0xff, 0xba, 0x89, 0xe5, 0xea, 0x40, 0xc8, 0x1d, 0x34, 0xa0, 0x1c, 0xab, 0xc8, 0xa0, 0x5d, 0xd8,
0xa6, 0x5c, 0xbd, 0xfe, 0x50, 0xae, 0xf7, 0x7b, 0xbd, 0x66, 0x7d, 0xd8, 0x6c, 0x70, 0xc1, 0x57,
0x07, 0xf2, 0x88, 0x02, 0x6e, 0x43, 0x99, 0x72, 0x84, 0xa3, 0x2b, 0x07, 0x1f, 0xf3, 0xba, 0x9c,
0x5f, 0xd8, 0x42, 0x25, 0xc8, 0x9f, 0x0e, 0xaa, 0x47, 0xf2, 0x40, 0x7a, 0xc5, 0xf7, 0xdf, 0x1f,
0x34, 0x7b, 0x42, 0xf6, 0xe0, 0xaf, 0x40, 0x48, 0xbe, 0x35, 0xe9, 0xfe, 0x86, 0x27, 0xd4, 0x6c,
0x04, 0x28, 0xd5, 0xaa, 0x52, 0x5b, 0x96, 0xea, 0xb8, 0x33, 0x18, 0x4a, 0x3c, 0xe8, 0xd2, 0x8c,
0xd0, 0x27, 0xac, 0x1c, 0xfd, 0xc7, 0x53, 0x58, 0x1f, 0x3c, 0x3f, 0xed, 0x0d, 0xbe, 0x40, 0x67,
0xf0, 0xa4, 0x45, 0x9c, 0x1b, 0x7e, 0x28, 0x81, 0xe2, 0x57, 0x1b, 0xb5, 0xf9, 0xfd, 0x4f, 0x6e,
0xfa, 0x79, 0x41, 0x04, 0x40, 0xcc, 0xa0, 0x3f, 0x66, 0xe1, 0x29, 0xbf, 0xbf, 0x6f, 0x58, 0xeb,
0x6d, 0x70, 0xdf, 0x76, 0x13, 0xaf, 0xe1, 0x5e, 0xf4, 0xb0, 0xf1, 0xdf, 0x6a, 0xa5, 0x1d, 0xf2,
0xc3, 0x74, 0xfc, 0xd8, 0x44, 0x31, 0x83, 0x7e, 0x82, 0x07, 0x89, 0xb3, 0xc5, 0xa1, 0x6f, 0x03,
0x73, 0xdb, 0xb5, 0x7e, 0x0d, 0xfb, 0x52, 0xe4, 0x0c, 0x89, 0x9f, 0x90, 0x3d, 0xbd, 0xcd, 0x4f,
0xba, 0xf6, 0x53, 0x8e, 0x2a, 0x66, 0xd0, 0x09, 0x54, 0x5a, 0xc4, 0xf1, 0x93, 0xac, 0x58, 0xda,
0x98, 0x2a, 0x9c, 0xeb, 0x5e, 0x71, 0x62, 0x06, 0xb5, 0xe1, 0x0e, 0xc7, 0x7a, 0x6f, 0xa4, 0x63,
0xd8, 0x6e, 0x11, 0x27, 0xf1, 0x12, 0x7c, 0x07, 0x9c, 0x3e, 0x6c, 0x4b, 0x0b, 0x38, 0xd7, 0xcd,
0xb9, 0x09, 0xf0, 0x57, 0xb0, 0xd9, 0x22, 0x4e, 0xf4, 0x35, 0x9d, 0xb6, 0xab, 0x4a, 0x8c, 0x16,
0xe1, 0xe6, 0x08, 0x52, 0x1c, 0x61, 0x29, 0xf7, 0x12, 0xad, 0x35, 0xa0, 0x74, 0x42, 0xdf, 0xe9,
0xa3, 0x13, 0x89, 0xa5, 0x30, 0x37, 0xbc, 0x7c, 0x96, 0xa0, 0x0c, 0x40, 0xa0, 0x09, 0x3d, 0x19,
0x49, 0xb5, 0xf0, 0x57, 0x40, 0x31, 0xce, 0xa5, 0x35, 0x80, 0x25, 0x88, 0x7f, 0x0d, 0x3b, 0x2d,
0xe2, 0x30, 0x50, 0x2d, 0x8a, 0x1a, 0x2f, 0x63, 0xc7, 0xaa, 0xbc, 0x37, 0x89, 0x7b, 0x08, 0x77,
0xbd, 0x4f, 0x51, 0xff, 0x9f, 0xa8, 0x5d, 0xa8, 0x30, 0x3c, 0xdf, 0xf0, 0x6f, 0x0b, 0x9b, 0x7e,
0xec, 0x1e, 0xec, 0x76, 0x75, 0x3b, 0xe5, 0xdc, 0x69, 0x96, 0xf1, 0x78, 0x39, 0x3c, 0xaf, 0x6a,
0x53, 0xa7, 0x2c, 0xf1, 0x2a, 0x94, 0x97, 0x1d, 0x3e, 0x4c, 0xaf, 0x0e, 0x79, 0xaa, 0xd9, 0x7f,
0xb0, 0x6c, 0xd8, 0x76, 0xa7, 0x0e, 0x83, 0xdb, 0x8a, 0xc2, 0xbd, 0x34, 0xc7, 0x37, 0x21, 0x2e,
0x2f, 0x47, 0x89, 0x19, 0x84, 0x61, 0xb7, 0xdd, 0x69, 0x50, 0x3d, 0x07, 0x35, 0x2a, 0x5e, 0xd1,
0x5a, 0x3e, 0xeb, 0xc6, 0x2d, 0x36, 0x01, 0xb5, 0x3b, 0x8d, 0xba, 0x62, 0xa8, 0x64, 0x1a, 0xee,
0xf2, 0x1a, 0xc0, 0x65, 0x8a, 0xb8, 0xcb, 0xb7, 0xe6, 0x55, 0xf0, 0x02, 0xfe, 0x74, 0x55, 0x3c,
0x5c, 0x8a, 0x4f, 0xd5, 0x29, 0x66, 0x50, 0x0d, 0xf6, 0x82, 0x6d, 0x55, 0xa7, 0xd3, 0x1b, 0xe0,
0xd2, 0xf7, 0xf4, 0x5b, 0x5f, 0x5c, 0x89, 0xaa, 0xe2, 0x75, 0xa7, 0xfb, 0x28, 0x39, 0x94, 0x5a,
0x91, 0x64, 0x1b, 0x2c, 0x1e, 0x4b, 0x41, 0xc5, 0x3a, 0xa1, 0xd6, 0x64, 0x25, 0x7b, 0xc9, 0x06,
0x5f, 0x01, 0x1c, 0x4b, 0x7e, 0xf1, 0x1c, 0xc5, 0x35, 0x95, 0xa8, 0xf0, 0x27, 0x24, 0x96, 0xac,
0xb8, 0x33, 0x0d, 0x94, 0x8f, 0xa5, 0x16, 0x71, 0xfc, 0x3a, 0x73, 0x02, 0x2f, 0x51, 0xa5, 0x4e,
0xe0, 0x25, 0x8b, 0xd3, 0x62, 0x06, 0xfd, 0x1e, 0x76, 0x8f, 0xa5, 0xba, 0x45, 0x14, 0x87, 0xc4,
0xbe, 0x53, 0xa0, 0xc4, 0xaf, 0xae, 0x52, 0xbe, 0x92, 0xec, 0x8b, 0xd7, 0xb1, 0x04, 0x2b, 0xfc,
0x0a, 0x8a, 0xec, 0xcb, 0x4b, 0x97, 0x3d, 0x1a, 0x13, 0x5a, 0x89, 0x7e, 0x5e, 0x4a, 0x8a, 0x8f,
0x0e, 0x89, 0x99, 0xcf, 0xb3, 0xa8, 0x05, 0xc5, 0xa6, 0x7a, 0x1e, 0x54, 0xde, 0xaf, 0x8b, 0x1f,
0xd7, 0x8c, 0x89, 0x19, 0xd4, 0x01, 0xc4, 0x03, 0x52, 0xec, 0x43, 0xed, 0xf2, 0x4f, 0x73, 0xfb,
0x7b, 0xe9, 0x9f, 0x07, 0xc5, 0x0c, 0xfa, 0x1e, 0x4a, 0x2d, 0xe2, 0x84, 0x9f, 0x15, 0xd3, 0xec,
0x75, 0xf9, 0xec, 0x63, 0xd8, 0xe3, 0xe2, 0x08, 0x88, 0xf5, 0x73, 0xfe, 0xe4, 0x7c, 0x3b, 0x1c,
0x0c, 0xdb, 0x2c, 0x28, 0x9e, 0xea, 0x67, 0xe1, 0x79, 0x7e, 0x91, 0x60, 0x5f, 0xf6, 0x35, 0x7c,
0xe9, 0xad, 0xb5, 0x1b, 0xdc, 0x31, 0x31, 0xdc, 0xeb, 0xe4, 0xbe, 0x5c, 0x86, 0x0c, 0xb1, 0x12,
0xbd, 0x62, 0x6e, 0x0d, 0xba, 0xfc, 0xdc, 0x27, 0x70, 0x2f, 0x76, 0xbd, 0xdc, 0x1a, 0x32, 0xfd,
0xc8, 0x7d, 0xae, 0x8e, 0x94, 0xed, 0xbd, 0xe3, 0x05, 0x23, 0xc3, 0x63, 0xbe, 0xb5, 0xe5, 0xb5,
0xaf, 0x5b, 0xd6, 0xd1, 0x96, 0xec, 0xd8, 0x84, 0x5f, 0xb4, 0x88, 0x53, 0x9d, 0x4e, 0x6f, 0x2e,
0xdf, 0xa5, 0x1d, 0xe1, 0x30, 0x5e, 0x7b, 0xb8, 0x09, 0x43, 0xcc, 0xa0, 0x29, 0x3c, 0x8d, 0xe4,
0xb1, 0xcb, 0x57, 0xbb, 0x4e, 0xf8, 0xb7, 0x3c, 0xb2, 0x98, 0x41, 0x2a, 0x3c, 0x62, 0xca, 0x58,
0xbe, 0x4e, 0x7a, 0x61, 0xf0, 0xad, 0x0c, 0xfd, 0x27, 0x10, 0x03, 0x43, 0xff, 0x73, 0x1f, 0xe8,
0x37, 0xf0, 0x51, 0xd4, 0x05, 0xde, 0x6d, 0xb9, 0xf4, 0x63, 0xfc, 0x2d, 0x7c, 0x18, 0x1a, 0xef,
0xdb, 0x99, 0xc1, 0x2d, 0x2c, 0x19, 0xc3, 0xfd, 0x88, 0xde, 0x17, 0x7e, 0x8b, 0x7d, 0xf3, 0xad,
0x9f, 0x9c, 0xc2, 0xbc, 0xe3, 0x21, 0x07, 0x4c, 0x8e, 0x61, 0x32, 0x9f, 0x2a, 0x6a, 0xf2, 0x9a,
0x4d, 0x72, 0xdd, 0xbc, 0xc0, 0x6f, 0xe1, 0x5e, 0xfa, 0x02, 0x55, 0x4d, 0x7b, 0x6f, 0xf0, 0xdf,
0xf9, 0xef, 0xd2, 0xc5, 0xdd, 0xcf, 0xcc, 0x8b, 0xf7, 0xdf, 0xfc, 0x10, 0xee, 0x87, 0xfa, 0x4c,
0x8e, 0xbf, 0xb3, 0x1e, 0xbb, 0xb0, 0xcb, 0x10, 0x17, 0x34, 0x78, 0xc3, 0x76, 0xd3, 0x6d, 0x6e,
0x0c, 0x1f, 0x46, 0xcd, 0x79, 0x99, 0x1e, 0xaf, 0x33, 0xe6, 0x5b, 0xc8, 0xf9, 0xf1, 0x75, 0x6b,
0x50, 0x55, 0xbe, 0x17, 0xfe, 0x09, 0xec, 0x84, 0x72, 0x0e, 0xb2, 0xc3, 0x77, 0x16, 0x70, 0xec,
0x8d, 0x12, 0xfe, 0x4c, 0xf1, 0x5d, 0xf1, 0xc6, 0xeb, 0xec, 0x3f, 0x71, 0x5f, 0xfe, 0x5f, 0x00,
0x00, 0x00, 0xff, 0xff, 0x06, 0xfc, 0xea, 0xaa, 0x21, 0x37, 0x00, 0x00,
0xcc, 0x62, 0x72, 0xce, 0xac, 0xb2, 0xc8, 0x7e, 0xfe, 0x45, 0x76, 0x49, 0x7e, 0x53, 0x36, 0x73,
0xb2, 0xc9, 0x26, 0x9b, 0xe4, 0x54, 0x55, 0xbf, 0xd1, 0x20, 0x29, 0x29, 0xb3, 0xab, 0xba, 0x75,
0xeb, 0xab, 0xaa, 0xfb, 0xaa, 0x5b, 0xb7, 0x01, 0x80, 0x89, 0x35, 0x57, 0x0f, 0xe7, 0x96, 0xe9,
0x98, 0xa8, 0x38, 0x78, 0x7e, 0x69, 0x0c, 0xbe, 0x90, 0x29, 0x49, 0x3c, 0x80, 0xbd, 0xda, 0xd4,
0x25, 0x8e, 0x69, 0x3a, 0xe7, 0xd5, 0x09, 0x31, 0x1c, 0x89, 0x38, 0x8e, 0x6e, 0x4c, 0x6c, 0x24,
0x40, 0x6e, 0xae, 0x1b, 0x95, 0xec, 0x07, 0xd9, 0x67, 0x05, 0x4c, 0x9b, 0xe2, 0xff, 0x64, 0xe1,
0x6e, 0xc0, 0xdc, 0x23, 0xce, 0xa5, 0x69, 0xbd, 0x91, 0x88, 0x75, 0xa1, 0xab, 0x04, 0x3d, 0x87,
0x3d, 0x8b, 0x4c, 0x74, 0xdb, 0x21, 0x96, 0x6c, 0x5a, 0xb2, 0x6b, 0xf8, 0x3d, 0x06, 0x90, 0xc7,
0x3b, 0x7e, 0xbf, 0x6f, 0x8d, 0x82, 0x31, 0x74, 0x00, 0xdb, 0x36, 0xb1, 0x2e, 0xf8, 0x1c, 0xd5,
0x34, 0x0c, 0xa2, 0x3a, 0x95, 0x15, 0x36, 0x61, 0x8b, 0x0f, 0xf4, 0xad, 0x3a, 0x27, 0xa3, 0xef,
0x61, 0xd5, 0xb9, 0x9a, 0x93, 0x4a, 0xee, 0x83, 0xec, 0xb3, 0xcd, 0xa3, 0x67, 0x87, 0x91, 0x53,
0x1c, 0x2e, 0xd9, 0xd5, 0xf0, 0x6a, 0x4e, 0x30, 0x9b, 0x85, 0x1e, 0x41, 0x71, 0xa6, 0xa8, 0x74,
0x19, 0x43, 0x99, 0x91, 0xca, 0x2a, 0x3b, 0x55, 0x61, 0xa6, 0xa8, 0x7d, 0xab, 0xa7, 0xcc, 0x08,
0x7a, 0x0c, 0xc5, 0xb1, 0xa5, 0x6b, 0x13, 0xc2, 0xc7, 0xd7, 0xd8, 0x38, 0x70, 0x12, 0x65, 0x10,
0xff, 0x73, 0x15, 0xee, 0x07, 0xcb, 0xd4, 0x4d, 0xc3, 0xb1, 0xcc, 0xe9, 0x94, 0x58, 0x81, 0xb8,
0x2a, 0xb0, 0x31, 0x37, 0x2f, 0x89, 0x45, 0x34, 0xef, 0xc4, 0x7e, 0x17, 0x7d, 0x00, 0x45, 0xef,
0x68, 0xca, 0x78, 0x4a, 0xbc, 0xe3, 0x45, 0x49, 0xe8, 0x97, 0x20, 0x9c, 0x29, 0xb6, 0x23, 0x47,
0xd9, 0x72, 0x5c, 0x0a, 0x94, 0x5e, 0x8f, 0xb0, 0x8a, 0x50, 0xd2, 0x74, 0x5b, 0x35, 0x2f, 0x88,
0xc5, 0xd8, 0x56, 0x19, 0x5b, 0x8c, 0x86, 0xf6, 0x21, 0x3f, 0x36, 0x0d, 0x8d, 0x8d, 0xaf, 0xb1,
0xf1, 0xa0, 0x8f, 0x0e, 0xe1, 0xce, 0x54, 0x37, 0xde, 0xc8, 0x53, 0x72, 0x41, 0xa6, 0xb2, 0x4d,
0x54, 0xd7, 0xd2, 0x9d, 0xab, 0xca, 0x3a, 0x63, 0xdb, 0xa6, 0x43, 0x5d, 0x3a, 0x22, 0x79, 0x03,
0xe8, 0x08, 0x76, 0x19, 0x13, 0x91, 0x6d, 0x7d, 0x36, 0x9f, 0x12, 0x79, 0xae, 0xe8, 0x96, 0x6e,
0x4c, 0x2a, 0x1b, 0x6c, 0xc6, 0x1d, 0x3e, 0x28, 0xb1, 0xb1, 0x01, 0x1f, 0x42, 0xbb, 0xb0, 0x3e,
0xb6, 0x64, 0xa2, 0x59, 0x95, 0x3c, 0x63, 0x5a, 0x1b, 0x5b, 0x4d, 0xcd, 0x42, 0x0f, 0x01, 0xce,
0xf5, 0xc9, 0xb9, 0x6c, 0xcf, 0x09, 0xd1, 0x2a, 0x05, 0x36, 0x54, 0xa0, 0x14, 0x89, 0x12, 0xe8,
0xf0, 0xd4, 0xbc, 0x94, 0x89, 0x41, 0xac, 0xc9, 0x55, 0x05, 0xf8, 0xf0, 0xd4, 0xbc, 0x6c, 0x32,
0x02, 0x95, 0xa2, 0xa2, 0x5d, 0x10, 0xcb, 0xd1, 0x6d, 0xba, 0x7c, 0x91, 0x4b, 0x31, 0x42, 0x42,
0x9f, 0x02, 0xf2, 0xb6, 0xea, 0xc9, 0x51, 0x37, 0x0d, 0xbb, 0x52, 0xe2, 0x27, 0xe3, 0x23, 0xf5,
0x70, 0x80, 0xae, 0xa7, 0x91, 0xb1, 0x3b, 0x91, 0xdf, 0x90, 0x2b, 0xbb, 0x52, 0xe6, 0xeb, 0x31,
0xca, 0x2b, 0x72, 0xc5, 0xf5, 0x69, 0xe9, 0x17, 0x8a, 0x7a, 0x55, 0xd9, 0xf4, 0xf4, 0xc9, 0xbb,
0xe8, 0x5b, 0xa8, 0xa8, 0x81, 0xfe, 0xe9, 0x5a, 0x67, 0xfa, 0xc4, 0xb5, 0x14, 0x8a, 0x5a, 0xd9,
0x62, 0xac, 0x77, 0xc3, 0xf1, 0x7a, 0x74, 0x18, 0x7d, 0x04, 0x9b, 0xb6, 0xa3, 0x38, 0xba, 0x2a,
0x2b, 0x9a, 0x66, 0x11, 0xdb, 0xae, 0x08, 0x6c, 0x42, 0x99, 0x53, 0xab, 0x9c, 0x28, 0xfe, 0x79,
0x15, 0x1e, 0xa5, 0xd8, 0x5a, 0xc7, 0x38, 0x33, 0xad, 0x19, 0x47, 0xaa, 0xc0, 0x86, 0x0f, 0x41,
0xcd, 0xad, 0x84, 0xfd, 0x2e, 0xfa, 0x04, 0xb6, 0xc7, 0xfe, 0x5c, 0xf9, 0x82, 0x58, 0x36, 0xdd,
0x17, 0x35, 0xba, 0x32, 0x16, 0x82, 0x81, 0xd7, 0x9c, 0x4e, 0xcd, 0x69, 0xa6, 0x18, 0xee, 0x99,
0xa2, 0x3a, 0xae, 0x45, 0x2c, 0x66, 0x75, 0x65, 0x1c, 0xa3, 0xa1, 0x53, 0x40, 0xb6, 0x3b, 0x9f,
0x9b, 0x96, 0x43, 0x34, 0xd9, 0xf6, 0xec, 0x9d, 0x19, 0x5e, 0x71, 0x99, 0x1b, 0x2e, 0xfa, 0x07,
0xde, 0x0e, 0x30, 0x02, 0x97, 0x91, 0x40, 0x50, 0x5d, 0xcb, 0x22, 0x86, 0x13, 0xc2, 0xae, 0xbd,
0x25, 0xec, 0x96, 0x87, 0x10, 0x80, 0x7e, 0x0c, 0x5b, 0xea, 0x54, 0xb1, 0x6d, 0xd9, 0x3c, 0x93,
0x35, 0x42, 0xa3, 0x00, 0x33, 0xee, 0x12, 0x2e, 0x33, 0x72, 0xff, 0xac, 0xc1, 0x88, 0x08, 0xc1,
0x2a, 0xf3, 0xf4, 0x0d, 0xe6, 0xe9, 0xac, 0x4d, 0x4d, 0xc2, 0x3e, 0x37, 0x2d, 0x87, 0xc7, 0x80,
0x3c, 0x8f, 0x11, 0x8c, 0xc2, 0x62, 0xc4, 0x13, 0x28, 0xe9, 0xb6, 0xac, 0x5c, 0x28, 0xfa, 0x94,
0xf9, 0x16, 0x37, 0xe1, 0xa2, 0x6e, 0x57, 0x7d, 0x12, 0xfa, 0x6b, 0xd8, 0xb7, 0x79, 0xec, 0x91,
0x0d, 0x1e, 0x8a, 0x64, 0x2f, 0xc0, 0x19, 0xca, 0xdc, 0x33, 0xea, 0xbb, 0x1e, 0x47, 0x24, 0x56,
0x11, 0xab, 0xa7, 0xcc, 0xd1, 0x0f, 0x70, 0x7f, 0xc9, 0xe4, 0xb9, 0x62, 0xb8, 0x9e, 0xc9, 0x57,
0xd2, 0x66, 0x0f, 0x14, 0xc3, 0x45, 0xdf, 0xc2, 0xbd, 0x25, 0xd3, 0x27, 0x86, 0xe7, 0x06, 0x7b,
0x69, 0x93, 0x5b, 0x86, 0xf8, 0x13, 0x08, 0x43, 0x4b, 0x9f, 0x4c, 0x88, 0x55, 0x65, 0xde, 0x21,
0x11, 0x07, 0xd5, 0x60, 0x33, 0x46, 0xa3, 0x86, 0x96, 0x7b, 0x56, 0x3c, 0xda, 0x8f, 0xe9, 0x26,
0xc6, 0x82, 0x13, 0x33, 0xa8, 0x90, 0xa9, 0xe4, 0x98, 0xf9, 0x15, 0x30, 0x6b, 0x8b, 0xff, 0x0e,
0x50, 0x8e, 0xb1, 0xa1, 0x4d, 0x58, 0xd1, 0x79, 0xd4, 0x2c, 0xe3, 0x15, 0x5d, 0xa3, 0xb6, 0x6d,
0x1a, 0x44, 0x3a, 0x37, 0xfd, 0xbb, 0xc0, 0xef, 0xd2, 0xc8, 0xa6, 0xdb, 0x74, 0xd6, 0x85, 0x1f,
0x20, 0x83, 0x3e, 0x7a, 0x00, 0x05, 0x7d, 0x36, 0x73, 0x9d, 0x48, 0x58, 0x0c, 0x09, 0xa8, 0x0b,
0x9b, 0xde, 0xd9, 0x25, 0x47, 0xa1, 0x56, 0xe8, 0x59, 0x9a, 0x98, 0x76, 0x1a, 0x29, 0xc6, 0xd9,
0xce, 0xe0, 0xc4, 0x5c, 0xf4, 0x6b, 0x40, 0xae, 0x3d, 0x6e, 0x29, 0xda, 0x84, 0xf8, 0xd1, 0x99,
0x68, 0xcc, 0xce, 0x8a, 0x47, 0x1f, 0xa7, 0x21, 0x8e, 0xa4, 0x5a, 0x82, 0xbb, 0x9d, 0xc1, 0x29,
0x18, 0x48, 0x81, 0xdd, 0x80, 0xda, 0xa0, 0x41, 0xdd, 0x07, 0xdf, 0x60, 0xe0, 0xbf, 0xbc, 0x16,
0x3c, 0x3a, 0xa1, 0x9d, 0xc1, 0xe9, 0x48, 0xa8, 0x03, 0xe5, 0x4b, 0xfd, 0x4c, 0xaf, 0x0e, 0x7c,
0x49, 0xe4, 0x19, 0xf4, 0x93, 0x34, 0xe8, 0xd3, 0x28, 0x63, 0x3b, 0x83, 0xe3, 0x33, 0xa9, 0x1c,
0x28, 0x21, 0xd8, 0x7e, 0xd5, 0x96, 0x1c, 0x85, 0xf9, 0xc5, 0x12, 0x39, 0x9c, 0x2e, 0x70, 0x53,
0x39, 0x2c, 0x62, 0xa0, 0xef, 0x20, 0x6f, 0xdb, 0xe7, 0x5d, 0x73, 0xa2, 0x1b, 0xcc, 0x6d, 0x8a,
0x47, 0x0f, 0x52, 0x35, 0x25, 0xb5, 0x19, 0x4f, 0x3b, 0x83, 0x03, 0x7e, 0x84, 0x41, 0xd0, 0xce,
0xd5, 0x79, 0x97, 0x28, 0x36, 0x69, 0x59, 0x8a, 0x41, 0xcf, 0x58, 0x64, 0x18, 0x4f, 0xd3, 0x30,
0x1a, 0xed, 0xfa, 0x20, 0xca, 0xdb, 0xce, 0xe0, 0x85, 0xf9, 0xe8, 0x18, 0x4a, 0x13, 0xcb, 0x74,
0xe7, 0x98, 0xa8, 0x84, 0x5a, 0x5f, 0x89, 0xe1, 0x7d, 0x90, 0x86, 0xd7, 0x8a, 0xf0, 0xb5, 0x33,
0x38, 0x36, 0x0f, 0xfd, 0x0e, 0x76, 0xa2, 0x7d, 0x89, 0xfc, 0x83, 0x4b, 0x0c, 0x95, 0xb0, 0xfb,
0x27, 0x19, 0xf7, 0x52, 0xf0, 0x7c, 0xfe, 0x76, 0x06, 0xa7, 0xe2, 0xa0, 0xe7, 0xb0, 0x3e, 0x99,
0xeb, 0x66, 0xc7, 0x60, 0xb7, 0xd6, 0x12, 0x6f, 0x6d, 0x0d, 0x3a, 0xfd, 0x0e, 0x95, 0x99, 0xc7,
0x8b, 0x1a, 0x00, 0x63, 0xc5, 0x3e, 0x97, 0x54, 0x4b, 0x9f, 0x3b, 0xec, 0x12, 0x4b, 0x7a, 0x86,
0x17, 0x17, 0xa8, 0xde, 0x6b, 0x01, 0x67, 0x3b, 0x8b, 0x23, 0xf3, 0x50, 0x15, 0x0a, 0xe7, 0xba,
0xe6, 0x81, 0x08, 0x29, 0x46, 0x15, 0x01, 0x69, 0x77, 0x1a, 0x01, 0x46, 0x38, 0x0b, 0xa9, 0xb0,
0xa7, 0x91, 0xf9, 0xd4, 0xbc, 0xf2, 0xe3, 0xf9, 0x90, 0xcc, 0xe6, 0x53, 0xc5, 0x21, 0x95, 0xed,
0x14, 0xfb, 0xe7, 0x78, 0x8d, 0xd4, 0x09, 0xed, 0x2c, 0x5e, 0x02, 0x85, 0x0e, 0x20, 0x37, 0x35,
0x27, 0x15, 0xc4, 0x10, 0xf7, 0x52, 0x10, 0xbb, 0xe6, 0xa4, 0x9d, 0xc5, 0x94, 0x09, 0xbd, 0x80,
0x0d, 0x2a, 0xa3, 0xbe, 0xeb, 0x54, 0xee, 0xa4, 0x08, 0x94, 0xf3, 0x53, 0x79, 0xf6, 0x5d, 0x7a,
0x14, 0x9f, 0x19, 0x7d, 0x0f, 0x05, 0xa6, 0x1f, 0x89, 0x18, 0x5a, 0x65, 0x27, 0xc5, 0x80, 0xbd,
0x99, 0x3e, 0x0f, 0x15, 0x43, 0x30, 0xa1, 0x56, 0x80, 0x0d, 0x4f, 0x55, 0xb5, 0x3c, 0xac, 0x73,
0x56, 0xf1, 0x2e, 0xec, 0xa6, 0xc6, 0x27, 0xf1, 0x3e, 0xdc, 0x5b, 0x1a, 0x66, 0xc4, 0x47, 0xf0,
0xe0, 0xba, 0x30, 0x21, 0xee, 0xc1, 0x4e, 0x9a, 0xaf, 0x47, 0x40, 0x17, 0x7d, 0x56, 0xfc, 0x0c,
0xb6, 0x12, 0x0e, 0x48, 0xc3, 0xef, 0x94, 0x36, 0x46, 0xb6, 0x97, 0xf3, 0x17, 0x70, 0x48, 0x10,
0xef, 0xc1, 0xdd, 0x25, 0xde, 0x26, 0x76, 0xe0, 0x4e, 0x8a, 0xa1, 0x53, 0x3c, 0x26, 0x0f, 0x76,
0x7f, 0x78, 0x78, 0x01, 0x01, 0xed, 0xc0, 0xda, 0x85, 0x32, 0x75, 0xf9, 0xcd, 0xb2, 0x86, 0x79,
0x47, 0xfc, 0x27, 0xb8, 0x7f, 0x8d, 0xcf, 0xdc, 0x00, 0x79, 0x00, 0x42, 0x67, 0x62, 0x98, 0x16,
0xe9, 0xbb, 0x4e, 0xff, 0xac, 0x6f, 0x69, 0xc4, 0xf2, 0xae, 0x9f, 0x05, 0x3a, 0xda, 0x83, 0x75,
0xb6, 0xa2, 0x5d, 0xc9, 0x7d, 0x90, 0x7b, 0xb6, 0x86, 0xbd, 0x9e, 0xf8, 0x1f, 0xd9, 0xe0, 0x6e,
0xe3, 0x3e, 0x86, 0x0e, 0xb9, 0xfd, 0xf4, 0xdc, 0x19, 0x5b, 0x71, 0xf3, 0x68, 0x27, 0x66, 0x05,
0x94, 0xab, 0xe7, 0xce, 0xb0, 0xcf, 0x84, 0x7e, 0x00, 0x98, 0xbb, 0xd3, 0xe9, 0x68, 0xde, 0x30,
0x2f, 0x79, 0xda, 0xb6, 0x79, 0xf4, 0x70, 0x61, 0x4a, 0xc7, 0x18, 0x04, 0x4c, 0x38, 0x32, 0x01,
0x7d, 0x0d, 0xc0, 0x5d, 0xba, 0xa9, 0x4d, 0xfc, 0xa7, 0xd2, 0xdd, 0x94, 0xe9, 0x74, 0x18, 0x47,
0x58, 0xc5, 0xaf, 0x61, 0x37, 0xd5, 0xc5, 0xd1, 0x23, 0x00, 0x9b, 0xb5, 0x22, 0x52, 0x8b, 0x50,
0xc4, 0x17, 0xb0, 0x93, 0xe6, 0xd6, 0x37, 0xce, 0xfb, 0xef, 0x2c, 0x3c, 0xb8, 0xce, 0x7f, 0x69,
0x6a, 0xea, 0x78, 0xed, 0x08, 0x44, 0x8c, 0x86, 0x5e, 0x7a, 0x6f, 0x42, 0x2e, 0xa7, 0x17, 0xb7,
0x0e, 0x0e, 0x87, 0x7e, 0x23, 0x7c, 0x21, 0x8a, 0x04, 0x4a, 0x51, 0x2a, 0xda, 0x86, 0xf2, 0xf1,
0xa8, 0xdb, 0x95, 0xa5, 0xe6, 0x70, 0xd8, 0xe9, 0xb5, 0x24, 0x21, 0x83, 0x8a, 0xb0, 0xd1, 0x6b,
0x0e, 0x4f, 0xfb, 0xf8, 0x95, 0x90, 0x45, 0x79, 0x58, 0x3d, 0xed, 0x1c, 0x77, 0x84, 0x15, 0xb4,
0x01, 0xb9, 0x91, 0x54, 0x13, 0x72, 0xa8, 0x0c, 0x85, 0x5a, 0x77, 0xd4, 0x1c, 0xf6, 0xfb, 0xc3,
0xb6, 0xb0, 0x8a, 0xee, 0xc0, 0xd6, 0x10, 0x77, 0x5a, 0xad, 0x26, 0x96, 0xab, 0xf5, 0x61, 0xa7,
0xdf, 0x93, 0x84, 0x35, 0xb1, 0x08, 0x85, 0x20, 0xc8, 0x88, 0x73, 0x28, 0xc7, 0x22, 0xc8, 0x5b,
0x9b, 0xcb, 0x67, 0x51, 0x3f, 0xd8, 0x3c, 0xba, 0xb7, 0xc0, 0xdd, 0x77, 0x9d, 0xd7, 0x94, 0xc1,
0x77, 0x91, 0x26, 0x6c, 0x25, 0x22, 0xcf, 0x3b, 0x79, 0xda, 0x25, 0xec, 0xd3, 0xb0, 0x80, 0xa9,
0x6b, 0xd9, 0x41, 0xf2, 0x2d, 0x39, 0xa6, 0xa5, 0x4c, 0x98, 0xea, 0x86, 0x29, 0xaa, 0x8b, 0xd2,
0xd0, 0x57, 0x90, 0x0f, 0x92, 0xfe, 0x15, 0x16, 0x1f, 0xe3, 0x9b, 0x3f, 0xd5, 0x8f, 0xf5, 0x20,
0xcb, 0x0f, 0x58, 0xc5, 0x3f, 0xe5, 0xa0, 0x14, 0x1d, 0x0a, 0xf2, 0xf8, 0x6c, 0x24, 0x8f, 0xdf,
0x87, 0xbc, 0xa6, 0xdb, 0x34, 0xef, 0xd3, 0x3c, 0x17, 0x0e, 0xfa, 0xd4, 0x2e, 0x2d, 0x32, 0x71,
0xa7, 0x8a, 0x63, 0x5a, 0x57, 0xcc, 0x43, 0x0a, 0x38, 0x42, 0x41, 0x3f, 0x42, 0x89, 0xa6, 0xc6,
0xba, 0x31, 0x91, 0x67, 0xa6, 0xc6, 0x33, 0xc9, 0xcd, 0x44, 0xec, 0xa6, 0x1b, 0x38, 0xe5, 0x4c,
0x27, 0xa6, 0x46, 0x70, 0xf1, 0x32, 0xec, 0xa0, 0x17, 0x50, 0x50, 0x5c, 0xe7, 0x9c, 0xcf, 0x5e,
0x4b, 0x51, 0x0b, 0x9d, 0x5d, 0x75, 0x9d, 0x73, 0x36, 0x35, 0xaf, 0x78, 0x2d, 0x9a, 0xf5, 0xaa,
0xe7, 0x8a, 0x61, 0x90, 0x29, 0x4b, 0x24, 0xcb, 0xd8, 0xef, 0xa2, 0x43, 0x58, 0x57, 0xe6, 0x72,
0x4d, 0x92, 0xbc, 0x24, 0xf0, 0xee, 0x02, 0x5c, 0x4d, 0x92, 0xea, 0x67, 0x13, 0xbc, 0xa6, 0xcc,
0x6b, 0x92, 0x84, 0x7e, 0xa4, 0x4f, 0x20, 0x9d, 0x3e, 0xab, 0x6a, 0x92, 0x24, 0x4f, 0x75, 0xdb,
0xa9, 0xe4, 0x59, 0xea, 0xbe, 0x74, 0x62, 0x99, 0xf3, 0xd7, 0x24, 0xa9, 0xab, 0xdb, 0x0e, 0xba,
0xcf, 0x2e, 0x72, 0x22, 0xdb, 0xb6, 0xee, 0x3f, 0xd4, 0xf3, 0x94, 0x20, 0xd9, 0xba, 0x46, 0x63,
0x9f, 0x41, 0x7e, 0x9e, 0x99, 0x86, 0xf7, 0x66, 0xf6, 0x7a, 0xe2, 0xbf, 0x66, 0xa1, 0xc0, 0x34,
0xe3, 0x50, 0xef, 0x3d, 0x84, 0x55, 0x26, 0x00, 0x6e, 0xc5, 0xfb, 0x8b, 0xaa, 0xa5, 0x5c, 0x4c,
0x02, 0x8c, 0x2f, 0x7a, 0xfa, 0x95, 0xf8, 0xe9, 0x11, 0xac, 0xb2, 0x7d, 0x70, 0x55, 0xb1, 0x36,
0xaa, 0x43, 0xf2, 0xdd, 0xe7, 0xbd, 0x47, 0xaf, 0xb1, 0xa1, 0xe4, 0x0c, 0xf1, 0x08, 0x20, 0x14,
0x01, 0x5d, 0x46, 0x92, 0x3a, 0x0d, 0xdf, 0x8e, 0x68, 0x1b, 0x09, 0x90, 0x1b, 0x48, 0xaf, 0xbc,
0xd7, 0x0b, 0x6d, 0x8a, 0x4f, 0xa0, 0x2c, 0x39, 0x16, 0x55, 0x35, 0xb1, 0x6d, 0x6a, 0xea, 0x02,
0xe4, 0x66, 0xf6, 0xc4, 0xaf, 0x92, 0xcd, 0xec, 0x89, 0xf8, 0x39, 0xa0, 0x18, 0x4b, 0xd5, 0xb2,
0x94, 0x2b, 0x6a, 0x92, 0x33, 0x7b, 0xc2, 0xda, 0xec, 0x1d, 0x55, 0xc0, 0x41, 0x5f, 0x3c, 0x84,
0x52, 0xf3, 0x82, 0x18, 0x8e, 0xe7, 0x4d, 0xd4, 0x44, 0xa9, 0xd2, 0x88, 0x41, 0xe3, 0x10, 0x83,
0xce, 0xe1, 0x08, 0x45, 0x54, 0x00, 0x18, 0x3f, 0x73, 0x6c, 0xb4, 0x0f, 0x1b, 0x8e, 0xcd, 0x16,
0xe4, 0xbb, 0x68, 0x67, 0xb0, 0x4f, 0x40, 0x7b, 0xb0, 0xe6, 0x8c, 0x4d, 0x93, 0xcb, 0x34, 0xdf,
0xce, 0x60, 0xde, 0x45, 0x15, 0x58, 0x77, 0x74, 0xc3, 0x79, 0xf1, 0x9c, 0x49, 0x35, 0x47, 0x33,
0x41, 0xde, 0xaf, 0xad, 0x41, 0xee, 0x42, 0x99, 0x8a, 0x5d, 0x58, 0x63, 0x4b, 0x50, 0xb1, 0x38,
0xe1, 0x2e, 0x78, 0x2d, 0xed, 0xb3, 0xe0, 0xf6, 0x5b, 0x49, 0x31, 0xab, 0x70, 0x6b, 0xc1, 0xb5,
0xf8, 0x7b, 0xd8, 0xa1, 0xbe, 0xdf, 0xd0, 0xad, 0xbe, 0x75, 0xac, 0x4f, 0x89, 0x7f, 0x50, 0x01,
0x72, 0x9a, 0xee, 0x67, 0x0b, 0xb4, 0x49, 0x8d, 0x6b, 0x6e, 0x91, 0x33, 0xfd, 0x67, 0x4f, 0xe8,
0x5e, 0x8f, 0x8a, 0xc4, 0x34, 0xa6, 0x57, 0xc7, 0xe6, 0x54, 0xf3, 0xaa, 0x14, 0x79, 0x1c, 0xa1,
0xd0, 0xeb, 0x2b, 0xb1, 0x82, 0x3d, 0x37, 0x0d, 0x9b, 0x70, 0x77, 0xb7, 0xdd, 0xa9, 0x33, 0x50,
0x9c, 0x73, 0xff, 0x1a, 0x0a, 0x29, 0xe2, 0xbf, 0x64, 0x61, 0x0b, 0x13, 0x45, 0x8b, 0x6e, 0xeb,
0x2b, 0x58, 0x3f, 0xe3, 0x0b, 0x65, 0x53, 0xee, 0xdf, 0xaa, 0xaa, 0x12, 0xdb, 0xd6, 0xc7, 0x53,
0xc2, 0xd7, 0xc6, 0x1e, 0x33, 0x55, 0xf1, 0x99, 0x3e, 0x25, 0x46, 0xf8, 0xe0, 0x0d, 0xfa, 0x34,
0x8a, 0xda, 0xf4, 0x7e, 0xe4, 0xf2, 0xc6, 0xbc, 0x43, 0xcf, 0x3f, 0x25, 0x06, 0x33, 0xdd, 0x1c,
0xa6, 0x4d, 0xb1, 0x01, 0x42, 0xb8, 0x1b, 0xef, 0x08, 0x0f, 0xa0, 0x60, 0x11, 0x45, 0xab, 0x9b,
0xae, 0xe1, 0x78, 0x7a, 0x08, 0x09, 0x54, 0x41, 0x9a, 0xe2, 0x28, 0x6c, 0xc5, 0x12, 0x66, 0x6d,
0xf1, 0xdf, 0xb2, 0x20, 0x9c, 0x5a, 0xba, 0x43, 0xfe, 0xc2, 0xa7, 0xda, 0xa3, 0x81, 0x69, 0x4e,
0x33, 0x5c, 0xae, 0x11, 0xaf, 0xc7, 0xaa, 0x4a, 0xae, 0xed, 0xf4, 0x4c, 0xa7, 0xf9, 0x33, 0x8d,
0x3e, 0x5e, 0x91, 0x32, 0x4a, 0x0b, 0xf6, 0xbd, 0x16, 0xd9, 0xf7, 0x47, 0xb0, 0x45, 0x77, 0xdc,
0x31, 0xce, 0x4c, 0x7f, 0xd7, 0x08, 0x56, 0xe7, 0xa1, 0xe6, 0x58, 0x5b, 0xfc, 0x03, 0x08, 0x21,
0x9b, 0x27, 0xa4, 0xb4, 0x6b, 0x80, 0x46, 0x0e, 0xfd, 0x1f, 0xf9, 0xb6, 0x73, 0x98, 0xb5, 0x29,
0x8d, 0xc5, 0x25, 0x5e, 0xe8, 0x0a, 0x62, 0xcf, 0xcc, 0xd4, 0x86, 0xba, 0x57, 0x17, 0xce, 0x61,
0xbf, 0x4b, 0xd5, 0xa6, 0xdb, 0x0d, 0xdd, 0xf2, 0xca, 0xa8, 0xbc, 0x23, 0xfe, 0x1d, 0x08, 0x41,
0x9e, 0x13, 0xf1, 0x59, 0x9e, 0xdc, 0x44, 0xed, 0x2c, 0xa4, 0xa0, 0x8f, 0x61, 0xd3, 0xd1, 0x67,
0xc4, 0x74, 0x1d, 0x89, 0xa8, 0xa6, 0xa1, 0xd9, 0x5e, 0x98, 0x4b, 0x50, 0xc5, 0x47, 0x50, 0x0a,
0xb0, 0x5f, 0x9a, 0xe3, 0x64, 0x6d, 0x44, 0x7c, 0x1a, 0x59, 0xfb, 0xa5, 0x39, 0x66, 0xe1, 0x5a,
0x80, 0x9c, 0xae, 0xf1, 0xf2, 0x4c, 0x19, 0xd3, 0xa6, 0xf8, 0x1a, 0x2a, 0xed, 0x4e, 0x03, 0xbb,
0x86, 0xa1, 0x1b, 0x93, 0x97, 0xe6, 0x98, 0x45, 0x5b, 0xcc, 0xac, 0x3e, 0x82, 0x98, 0x63, 0xd5,
0x16, 0x04, 0xab, 0x17, 0xb3, 0x8e, 0xe6, 0x4b, 0x89, 0xb6, 0xa9, 0x62, 0x6d, 0xd3, 0xb5, 0x54,
0xe2, 0x45, 0x5d, 0xaf, 0x27, 0xfe, 0x01, 0xb6, 0x22, 0x27, 0x67, 0x70, 0x9f, 0x40, 0xee, 0x27,
0x73, 0xcc, 0xf0, 0x92, 0xe1, 0x37, 0xba, 0x51, 0x4c, 0xb9, 0xa8, 0x94, 0x74, 0xfb, 0x58, 0x37,
0x74, 0xfb, 0x3c, 0xb8, 0x9a, 0x23, 0x94, 0xd0, 0x5b, 0x5f, 0xda, 0xa6, 0x11, 0x5e, 0xce, 0x3e,
0x45, 0x3c, 0x84, 0x62, 0xb7, 0xd9, 0x08, 0xee, 0xfe, 0xc7, 0x50, 0x1c, 0xb3, 0x6a, 0xb6, 0x1a,
0xf8, 0x46, 0x19, 0x03, 0x23, 0x31, 0xe7, 0x10, 0x7f, 0x86, 0x7b, 0x23, 0xa9, 0xf6, 0x1e, 0x59,
0xca, 0xd7, 0x0b, 0x59, 0xca, 0xfd, 0x78, 0x8a, 0xc5, 0x1e, 0x54, 0x29, 0x79, 0xca, 0x9f, 0xd7,
0x60, 0x33, 0x3e, 0x48, 0xcd, 0x8c, 0x18, 0x3c, 0x29, 0xf1, 0xbe, 0x10, 0x78, 0x5d, 0xaa, 0xc0,
0x0b, 0x5d, 0xf3, 0xef, 0x99, 0x0b, 0x5d, 0xe3, 0x1f, 0x5f, 0xfc, 0x3b, 0x8f, 0x36, 0x17, 0x2a,
0xb5, 0xfc, 0x0b, 0x46, 0xbc, 0x52, 0xcb, 0x6a, 0xd6, 0xa6, 0xe6, 0xaa, 0x8e, 0xf7, 0x01, 0xc3,
0xef, 0x32, 0x85, 0x12, 0x4b, 0x57, 0x78, 0x6e, 0x41, 0x15, 0xca, 0x7a, 0xe8, 0x11, 0x14, 0x5d,
0x9b, 0xc8, 0xf5, 0x46, 0x5d, 0x6e, 0xd6, 0x4f, 0xbc, 0xa2, 0x7e, 0xc1, 0xb5, 0x49, 0xbd, 0x51,
0x6f, 0xd6, 0x4f, 0x68, 0x26, 0x40, 0xc7, 0x71, 0xaf, 0xd1, 0x91, 0xbc, 0x6a, 0x7e, 0xde, 0xb5,
0x09, 0xeb, 0xa3, 0x67, 0x20, 0xd0, 0xc1, 0x76, 0xa7, 0x21, 0xbf, 0x6a, 0xfe, 0xa6, 0xd6, 0xaf,
0xe2, 0x86, 0x97, 0x2d, 0x6c, 0xba, 0x36, 0x69, 0x77, 0x1a, 0x3e, 0x15, 0x89, 0x50, 0xf6, 0x39,
0x4f, 0xfa, 0x23, 0xa9, 0xe9, 0x55, 0x42, 0x8b, 0x9c, 0x8d, 0x91, 0xfc, 0xad, 0x50, 0x1e, 0x5c,
0x3d, 0xf5, 0xaa, 0x9d, 0x05, 0xce, 0x81, 0xab, 0xa7, 0xe8, 0x2e, 0x6c, 0xd0, 0xf1, 0xd1, 0x89,
0xe4, 0x15, 0x33, 0xd7, 0x5d, 0x9b, 0x8c, 0x4e, 0x24, 0xf4, 0x10, 0x80, 0x0e, 0x48, 0x4d, 0xdc,
0xa9, 0x76, 0xfd, 0x42, 0xbe, 0x6b, 0x13, 0x4e, 0x40, 0x2f, 0x61, 0xd3, 0x32, 0x34, 0xdd, 0x0e,
0x6b, 0xcc, 0xbc, 0x32, 0xf2, 0xe1, 0x35, 0x8a, 0x6c, 0x3a, 0xe7, 0xc4, 0x32, 0x88, 0x83, 0xcb,
0x6c, 0x6a, 0xa0, 0xc2, 0x13, 0x10, 0x54, 0x4d, 0x95, 0x89, 0x3a, 0x0b, 0xd1, 0xb6, 0x6e, 0x8f,
0xb6, 0xa9, 0x6a, 0x6a, 0x53, 0x9d, 0x05, 0x70, 0x55, 0x28, 0xb9, 0xb3, 0xc8, 0xc6, 0x78, 0xcd,
0xe4, 0xd1, 0x35, 0x50, 0xa3, 0x13, 0x09, 0x17, 0xdd, 0x59, 0xb8, 0xa3, 0x2f, 0x60, 0x57, 0x23,
0x17, 0x32, 0x8d, 0x8b, 0xf2, 0xb9, 0xae, 0xc9, 0x6f, 0xc8, 0xd5, 0xd8, 0x54, 0x2c, 0x8d, 0x55,
0x37, 0x0a, 0x18, 0x69, 0xe4, 0x82, 0xc6, 0x9f, 0xb6, 0xae, 0xbd, 0xf2, 0x46, 0xd0, 0x27, 0x80,
0x62, 0x53, 0x66, 0xa6, 0x6b, 0x13, 0x56, 0xdd, 0x28, 0xe0, 0xad, 0x90, 0xff, 0x84, 0x92, 0xd1,
0x2f, 0x40, 0x88, 0x31, 0x5b, 0xca, 0x25, 0x2b, 0x67, 0x14, 0x70, 0x39, 0x64, 0xc5, 0xca, 0xa5,
0x38, 0x80, 0xbd, 0xf4, 0x53, 0xb3, 0x6c, 0xd2, 0xb4, 0x1d, 0xf6, 0xc9, 0xc3, 0x73, 0xb2, 0x3c,
0x25, 0x54, 0x35, 0xcd, 0x42, 0xf7, 0x20, 0x4f, 0xf1, 0xd9, 0x18, 0xb7, 0xff, 0x0d, 0x8d, 0x5c,
0xd0, 0x21, 0xf1, 0x07, 0xd8, 0x5e, 0x38, 0x3c, 0x8d, 0xc8, 0xaa, 0x66, 0x99, 0x33, 0xcf, 0x85,
0x78, 0x87, 0xc6, 0x30, 0x7a, 0x29, 0xf9, 0x75, 0x66, 0xda, 0x16, 0xff, 0x39, 0x0b, 0x8f, 0x02,
0xc9, 0xbf, 0x7b, 0x04, 0xa8, 0x2d, 0x44, 0x80, 0x78, 0x61, 0xd3, 0x5f, 0xa2, 0x63, 0x38, 0xc4,
0x3a, 0x53, 0x54, 0x92, 0x12, 0x0c, 0x64, 0x78, 0xc2, 0xdf, 0xa1, 0x44, 0x5b, 0xca, 0x8e, 0xbe,
0x83, 0x55, 0x96, 0xaa, 0xf3, 0x2a, 0xfb, 0x6d, 0x17, 0x61, 0x73, 0xc4, 0x3f, 0xe6, 0xe0, 0xde,
0x72, 0xe4, 0xb4, 0xbb, 0xf1, 0x47, 0xef, 0x1e, 0xe4, 0xef, 0xc6, 0x4f, 0x6e, 0xb7, 0xda, 0x61,
0x24, 0x61, 0xa7, 0xa1, 0x7c, 0xee, 0x7d, 0xb0, 0x7a, 0xee, 0x87, 0xea, 0x90, 0x42, 0xf3, 0x06,
0x83, 0x38, 0x33, 0xc5, 0x7e, 0xf3, 0xdc, 0x8b, 0x55, 0x41, 0x3f, 0x1a, 0x09, 0xd7, 0xe2, 0x91,
0xb0, 0x0f, 0x48, 0x3b, 0x57, 0xe7, 0xfc, 0xc3, 0x44, 0x90, 0xdb, 0xf3, 0xc2, 0xfa, 0xe3, 0xd8,
0x26, 0x1b, 0xed, 0xfa, 0x20, 0xce, 0x86, 0x53, 0xa6, 0xa2, 0xa7, 0x50, 0xf6, 0xd5, 0xd0, 0x31,
0x46, 0x36, 0xf1, 0x42, 0x5c, 0x9c, 0x28, 0xd6, 0x61, 0x95, 0xbd, 0xc1, 0x00, 0xd6, 0x4f, 0xaa,
0xbd, 0x51, 0xb5, 0x2b, 0x64, 0xd0, 0x16, 0x14, 0xe9, 0x1a, 0x72, 0xbd, 0xdb, 0x69, 0xf6, 0x86,
0x42, 0x36, 0x20, 0x48, 0x4d, 0xfc, 0xba, 0x89, 0x85, 0x15, 0xfa, 0xdc, 0x1f, 0xf5, 0x4e, 0xaa,
0xbd, 0x6a, 0xab, 0xd9, 0x10, 0x72, 0xe2, 0xff, 0xe6, 0x00, 0x2d, 0xee, 0x2a, 0xcc, 0xe6, 0x07,
0xa6, 0x15, 0xdc, 0x51, 0x21, 0x05, 0x3d, 0x83, 0x2d, 0xde, 0x0b, 0xc4, 0xed, 0x99, 0x71, 0x92,
0xcc, 0x4a, 0x6c, 0x44, 0xb1, 0x59, 0x56, 0xe7, 0x49, 0x3c, 0x24, 0xa0, 0x03, 0x10, 0x0c, 0xd3,
0xa1, 0x0f, 0x4b, 0xd3, 0xd2, 0x1d, 0x85, 0x7d, 0x23, 0xe1, 0x89, 0xd7, 0x02, 0x1d, 0x1d, 0x02,
0xd2, 0xcc, 0x9e, 0xe9, 0xd4, 0x74, 0x43, 0x0b, 0x97, 0xe5, 0xba, 0x48, 0x19, 0xa1, 0xd9, 0x8b,
0xaa, 0x4c, 0xa7, 0x63, 0x45, 0x7d, 0xe3, 0x95, 0x77, 0xf9, 0x35, 0x92, 0xa0, 0xa2, 0xe7, 0xb0,
0x6e, 0x29, 0xc6, 0x84, 0xd8, 0x95, 0x0d, 0x66, 0xc5, 0x0f, 0x96, 0xa8, 0x0c, 0x53, 0x26, 0xec,
0xf1, 0xa2, 0x63, 0xd8, 0x30, 0xe7, 0xfc, 0x13, 0x13, 0x7f, 0xa7, 0xfe, 0xd5, 0x0d, 0x9a, 0x3e,
0xec, 0x73, 0xf6, 0xa6, 0xe1, 0x58, 0x57, 0xd8, 0x9f, 0x8c, 0xea, 0x50, 0xe4, 0xdf, 0x51, 0xdb,
0xa6, 0xed, 0xd8, 0x95, 0x02, 0xc3, 0x7a, 0xb2, 0x0c, 0x2b, 0xe0, 0xc4, 0xd1, 0x59, 0xfb, 0xdf,
0x41, 0x29, 0x8a, 0x4e, 0x6f, 0xe2, 0x37, 0xe4, 0xca, 0xd3, 0x1b, 0x6d, 0xc6, 0x2b, 0x22, 0x05,
0xaf, 0x22, 0xf2, 0xdd, 0xca, 0x37, 0x59, 0xd1, 0x84, 0xad, 0xc4, 0x19, 0x59, 0x46, 0x43, 0x1b,
0x5d, 0xf3, 0x32, 0xa8, 0x8b, 0x46, 0x28, 0xc1, 0xf8, 0x68, 0x3e, 0x27, 0x7e, 0x04, 0x8c, 0x50,
0x02, 0x9d, 0xb3, 0xec, 0x34, 0xaa, 0x73, 0x4a, 0x10, 0xbf, 0x81, 0x9d, 0xb4, 0x13, 0xb1, 0x57,
0xa9, 0xa2, 0x06, 0xaf, 0x52, 0x45, 0x65, 0x59, 0xdf, 0xdc, 0xc3, 0x5f, 0xd1, 0xe7, 0xe2, 0x06,
0xac, 0x35, 0x67, 0x73, 0xe7, 0xea, 0xe0, 0x9b, 0xc8, 0xcf, 0x1a, 0x16, 0x7f, 0x3d, 0x81, 0x36,
0x20, 0xd7, 0xab, 0x0e, 0x84, 0x0c, 0xca, 0xc3, 0xea, 0xa0, 0xda, 0x1b, 0x09, 0x59, 0xb4, 0x0e,
0x2b, 0xad, 0x9e, 0xb0, 0x72, 0xf0, 0x29, 0x08, 0xc9, 0x5a, 0x24, 0x1d, 0x1b, 0x79, 0xdc, 0x8d,
0xfe, 0x69, 0x4f, 0xc8, 0x52, 0x80, 0xfe, 0xf1, 0xb1, 0xb0, 0x72, 0xf0, 0x19, 0x40, 0x58, 0x7b,
0xa4, 0x9e, 0x86, 0x3b, 0x52, 0xa7, 0xd7, 0xe2, 0x65, 0xb5, 0xe3, 0x6a, 0xb7, 0x4b, 0x3b, 0xac,
0xac, 0x56, 0xeb, 0x0f, 0xdb, 0xc2, 0xca, 0xc1, 0x7f, 0x65, 0x61, 0xc3, 0x2b, 0x78, 0xa1, 0x02,
0xac, 0xf5, 0x46, 0x27, 0xf2, 0x17, 0x42, 0xc6, 0x6f, 0x1e, 0x09, 0x59, 0xbf, 0xf9, 0xa5, 0xb0,
0xe2, 0x37, 0x9f, 0x0b, 0x39, 0xbf, 0xf9, 0x95, 0xb0, 0xea, 0x37, 0x5f, 0x08, 0x6b, 0x7e, 0xf3,
0x6b, 0x61, 0xdd, 0x6f, 0x7e, 0x23, 0x6c, 0xf8, 0xcd, 0x6f, 0x85, 0x3c, 0xdd, 0x11, 0x5b, 0xe2,
0x73, 0xa1, 0x10, 0xb4, 0xbf, 0x10, 0x20, 0x68, 0x1f, 0x09, 0xc5, 0xa0, 0xfd, 0xa5, 0x50, 0x0a,
0xda, 0xcf, 0x85, 0x72, 0xd0, 0xfe, 0x4a, 0xd8, 0x0c, 0xda, 0x2f, 0x84, 0xad, 0xa0, 0xfd, 0xb5,
0x20, 0x04, 0xed, 0x6f, 0x84, 0xed, 0xa0, 0xfd, 0xad, 0x80, 0xfc, 0xf6, 0xd1, 0xe7, 0xc2, 0x9d,
0x83, 0x4f, 0xa1, 0x14, 0x2d, 0xda, 0x51, 0xe1, 0x75, 0xfb, 0xa7, 0x5c, 0x9e, 0xed, 0x4e, 0xab,
0x2d, 0x64, 0x29, 0xfb, 0xb0, 0xdf, 0x6a, 0x75, 0x9b, 0xc2, 0xca, 0x41, 0x03, 0xb6, 0x12, 0xa5,
0x28, 0x2a, 0xcb, 0x51, 0xef, 0x55, 0x8f, 0xca, 0x3e, 0x43, 0xb5, 0x51, 0x1d, 0x70, 0x1d, 0x48,
0xc3, 0xaa, 0xb0, 0x82, 0xee, 0xc0, 0x96, 0x34, 0xac, 0xca, 0xc7, 0xd5, 0x4e, 0xb7, 0xff, 0xba,
0x89, 0xe5, 0xea, 0x40, 0xc8, 0x1d, 0x34, 0xa0, 0x1c, 0xab, 0xc8, 0xa0, 0x5d, 0xd8, 0xa6, 0x5c,
0xbd, 0xfe, 0x50, 0xae, 0xf7, 0x7b, 0xbd, 0x66, 0x7d, 0xd8, 0x6c, 0x70, 0xc1, 0x57, 0x07, 0xf2,
0x88, 0x02, 0x6e, 0x43, 0x99, 0x72, 0x84, 0xa3, 0x2b, 0x07, 0x1f, 0xf3, 0xba, 0x9c, 0x5f, 0xd8,
0x42, 0x25, 0xc8, 0x9f, 0x0e, 0xaa, 0x47, 0xf2, 0x40, 0x7a, 0xc5, 0xf7, 0xdf, 0x1f, 0x34, 0x7b,
0x42, 0xf6, 0xe0, 0x6f, 0x40, 0x48, 0xbe, 0x35, 0xe9, 0xfe, 0x86, 0x27, 0xd4, 0x6c, 0x04, 0x28,
0xd5, 0xaa, 0x52, 0x5b, 0x96, 0xea, 0xb8, 0x33, 0x18, 0x4a, 0x3c, 0xe8, 0xd2, 0x8c, 0xd0, 0x27,
0xac, 0x1c, 0xfd, 0xe9, 0x63, 0x58, 0x1f, 0x3c, 0x3f, 0xed, 0x0d, 0xbe, 0x40, 0x67, 0xf0, 0xa4,
0x45, 0x9c, 0x1b, 0x7e, 0x28, 0x81, 0xe2, 0x57, 0x1b, 0xb5, 0xf9, 0xfd, 0x4f, 0x6e, 0xfa, 0x79,
0x41, 0x04, 0x40, 0xcc, 0xa0, 0x3f, 0x66, 0xe1, 0x29, 0xbf, 0xbf, 0x6f, 0x58, 0xeb, 0x6d, 0x70,
0xdf, 0x76, 0x13, 0xaf, 0xe1, 0x5e, 0xf4, 0xb0, 0xf1, 0xdf, 0x6a, 0xa5, 0x1d, 0xf2, 0xc3, 0x74,
0xfc, 0xd8, 0x44, 0x31, 0x83, 0x7e, 0x82, 0x07, 0x89, 0xb3, 0xc5, 0xa1, 0x6f, 0x03, 0x73, 0xdb,
0xb5, 0x7e, 0x0d, 0xfb, 0x52, 0xe4, 0x0c, 0x89, 0x9f, 0x90, 0x3d, 0xbd, 0xcd, 0x4f, 0xba, 0xf6,
0x53, 0x8e, 0x2a, 0x66, 0xd0, 0x09, 0x54, 0x5a, 0xc4, 0xf1, 0x93, 0xac, 0x58, 0xda, 0x98, 0x2a,
0x9c, 0xeb, 0x5e, 0x71, 0x62, 0x06, 0xb5, 0xe1, 0x0e, 0xc7, 0x7a, 0x6f, 0xa4, 0x63, 0xd8, 0x6e,
0x11, 0x27, 0xf1, 0x12, 0x7c, 0x07, 0x9c, 0x3e, 0x6c, 0x4b, 0x0b, 0x38, 0xd7, 0xcd, 0xb9, 0x09,
0xf0, 0x57, 0xb0, 0xd9, 0x22, 0x4e, 0xf4, 0x35, 0x9d, 0xb6, 0xab, 0x4a, 0x8c, 0x16, 0xe1, 0xe6,
0x08, 0x52, 0x1c, 0x61, 0x29, 0xf7, 0x12, 0xad, 0x35, 0xa0, 0x74, 0x42, 0xdf, 0xe9, 0xa3, 0x13,
0x89, 0xa5, 0x30, 0x37, 0xbc, 0x7c, 0x96, 0xa0, 0x0c, 0x40, 0xa0, 0x09, 0x3d, 0x19, 0x49, 0xb5,
0xf0, 0x57, 0x40, 0x31, 0xce, 0xa5, 0x35, 0x80, 0x25, 0x88, 0x7f, 0x0b, 0x3b, 0x2d, 0xe2, 0x30,
0x50, 0x2d, 0x8a, 0x1a, 0x2f, 0x63, 0xc7, 0xaa, 0xbc, 0x37, 0x89, 0x7b, 0x08, 0x77, 0xbd, 0x4f,
0x51, 0xff, 0x9f, 0xa8, 0x5d, 0xa8, 0x30, 0x3c, 0xdf, 0xf0, 0x6f, 0x0b, 0x9b, 0x7e, 0xec, 0x1e,
0xec, 0x76, 0x75, 0x3b, 0xe5, 0xdc, 0x69, 0x96, 0xf1, 0x78, 0x39, 0x3c, 0xaf, 0x6a, 0x53, 0xa7,
0x2c, 0xf1, 0x2a, 0x94, 0x97, 0x1d, 0x3e, 0x4c, 0xaf, 0x0e, 0x79, 0xaa, 0xd9, 0x7f, 0xb0, 0x6c,
0xd8, 0x76, 0xa7, 0x0e, 0x83, 0xdb, 0x8a, 0xc2, 0xbd, 0x34, 0xc7, 0x37, 0x21, 0x2e, 0x2f, 0x47,
0x89, 0x19, 0x84, 0x61, 0xb7, 0xdd, 0x69, 0x50, 0x3d, 0x07, 0x35, 0x2a, 0x5e, 0xd1, 0x5a, 0x3e,
0xeb, 0xc6, 0x2d, 0x36, 0x01, 0xb5, 0x3b, 0x8d, 0xba, 0x62, 0xa8, 0x64, 0x1a, 0xee, 0xf2, 0x1a,
0xc0, 0x65, 0x8a, 0xb8, 0xcb, 0xb7, 0xe6, 0x55, 0xf0, 0x02, 0xfe, 0x74, 0x55, 0x3c, 0x5c, 0x8a,
0x4f, 0xd5, 0x29, 0x66, 0x50, 0x0d, 0xf6, 0x82, 0x6d, 0x55, 0xa7, 0xd3, 0x1b, 0xe0, 0xd2, 0xf7,
0xf4, 0x5b, 0x5f, 0x5c, 0x89, 0xaa, 0xe2, 0x75, 0xa7, 0xfb, 0x28, 0x39, 0x94, 0x5a, 0x91, 0x64,
0x1b, 0x2c, 0x1e, 0x4b, 0x41, 0xc5, 0x3a, 0xa1, 0xd6, 0x64, 0x25, 0x7b, 0xc9, 0x06, 0x5f, 0x01,
0x1c, 0x4b, 0x7e, 0xf1, 0x1c, 0xc5, 0x35, 0x95, 0xa8, 0xf0, 0x27, 0x24, 0x96, 0xac, 0xb8, 0x33,
0x0d, 0x94, 0x8f, 0xa5, 0x16, 0x71, 0xfc, 0x3a, 0x73, 0x02, 0x2f, 0x51, 0xa5, 0x4e, 0xe0, 0x25,
0x8b, 0xd3, 0x62, 0x06, 0xfd, 0x1e, 0x76, 0x8f, 0xa5, 0xba, 0x45, 0x14, 0x87, 0xc4, 0xbe, 0x53,
0xa0, 0xc4, 0xaf, 0xae, 0x52, 0xbe, 0x92, 0xec, 0x8b, 0xd7, 0xb1, 0x04, 0x2b, 0xfc, 0x0a, 0x8a,
0xec, 0xcb, 0x4b, 0x97, 0x3d, 0x1a, 0x13, 0x5a, 0x89, 0x7e, 0x5e, 0x4a, 0x8a, 0x8f, 0x0e, 0x89,
0x99, 0xcf, 0xb3, 0xa8, 0x05, 0xc5, 0xa6, 0x7a, 0x1e, 0x54, 0xde, 0xaf, 0x8b, 0x1f, 0xd7, 0x8c,
0x89, 0x19, 0xd4, 0x01, 0xc4, 0x03, 0x52, 0xec, 0x43, 0xed, 0xf2, 0x4f, 0x73, 0xfb, 0x7b, 0xe9,
0x9f, 0x07, 0xc5, 0x0c, 0xfa, 0x1e, 0x4a, 0x2d, 0xe2, 0x84, 0x9f, 0x15, 0xd3, 0xec, 0x75, 0xf9,
0xec, 0x63, 0xd8, 0xe3, 0xe2, 0x08, 0x88, 0xf5, 0x73, 0xfe, 0xe4, 0x7c, 0x3b, 0x1c, 0x0c, 0xdb,
0x2c, 0x28, 0x9e, 0xea, 0x67, 0xe1, 0x79, 0x7e, 0x91, 0x60, 0x5f, 0xf6, 0x35, 0x7c, 0xe9, 0xad,
0xb5, 0x1b, 0xdc, 0x31, 0x31, 0xdc, 0xeb, 0xe4, 0xbe, 0x5c, 0x86, 0x0c, 0xb1, 0x12, 0xbd, 0x62,
0x6e, 0x0d, 0xba, 0xfc, 0xdc, 0x27, 0x70, 0x2f, 0x76, 0xbd, 0xdc, 0x1a, 0x32, 0xfd, 0xc8, 0x7d,
0xae, 0x8e, 0x94, 0xed, 0xbd, 0xe3, 0x05, 0x23, 0xc3, 0x63, 0xbe, 0xb5, 0xe5, 0xb5, 0xaf, 0x5b,
0xd6, 0xd1, 0x96, 0xec, 0xd8, 0x84, 0x5f, 0xb4, 0x88, 0x53, 0x9d, 0x4e, 0x6f, 0x2e, 0xdf, 0xa5,
0x1d, 0xe1, 0x30, 0x5e, 0x7b, 0xb8, 0x09, 0x43, 0xcc, 0xa0, 0x29, 0x3c, 0x8d, 0xe4, 0xb1, 0xcb,
0x57, 0xbb, 0x4e, 0xf8, 0xb7, 0x3c, 0xb2, 0x98, 0x41, 0x2a, 0x3c, 0x62, 0xca, 0x58, 0xbe, 0x4e,
0x7a, 0x61, 0xf0, 0xad, 0x0c, 0xfd, 0x27, 0x10, 0x03, 0x43, 0xff, 0x4b, 0x1f, 0xe8, 0x37, 0xf0,
0x51, 0xd4, 0x05, 0xde, 0x6d, 0xb9, 0xf4, 0x63, 0xfc, 0x3d, 0x7c, 0x18, 0x1a, 0xef, 0xdb, 0x99,
0xc1, 0x2d, 0x2c, 0x19, 0xc3, 0xfd, 0x88, 0xde, 0x17, 0x7e, 0x8b, 0x7d, 0xf3, 0xad, 0x9f, 0x9c,
0xc2, 0xbc, 0xe3, 0x21, 0x07, 0x4c, 0x8e, 0x61, 0x32, 0x9f, 0x2a, 0x6a, 0xf2, 0x9a, 0x4d, 0x72,
0xdd, 0xbc, 0xc0, 0x6f, 0xe1, 0x5e, 0xfa, 0x02, 0x55, 0x4d, 0x7b, 0x6f, 0xf0, 0xdf, 0xf9, 0xef,
0xd2, 0xc5, 0xdd, 0xcf, 0xcc, 0x8b, 0xf7, 0xdf, 0xfc, 0x10, 0xee, 0x87, 0xfa, 0x4c, 0x8e, 0xbf,
0xb3, 0x1e, 0xbb, 0xb0, 0xcb, 0x10, 0x17, 0x34, 0x78, 0xc3, 0x76, 0xd3, 0x6d, 0x6e, 0x0c, 0x1f,
0x46, 0xcd, 0x79, 0x99, 0x1e, 0xaf, 0x33, 0xe6, 0x5b, 0xc8, 0xf9, 0xf1, 0x75, 0x6b, 0x50, 0x55,
0xbe, 0x17, 0xfe, 0xf7, 0x90, 0x6f, 0xd4, 0x6a, 0x8a, 0xfa, 0xc6, 0x9d, 0xbf, 0x83, 0xd7, 0xfd,
0x00, 0x85, 0x46, 0x0d, 0x13, 0x9b, 0xee, 0xed, 0x1d, 0xa6, 0x9f, 0xc0, 0x4e, 0xa8, 0xe4, 0x20,
0x35, 0x7d, 0x67, 0xed, 0xc6, 0x1e, 0x48, 0xe1, 0x6f, 0x24, 0xdf, 0xc3, 0x5a, 0xee, 0x84, 0x78,
0xbe, 0x94, 0xde, 0x15, 0x6d, 0xbc, 0xce, 0xfe, 0xde, 0xf7, 0xe5, 0xff, 0x05, 0x00, 0x00, 0xff,
0xff, 0x50, 0x12, 0x00, 0x30, 0xec, 0x37, 0x00, 0x00,
}

View File

@ -82,11 +82,17 @@ service P4WNP1 {
rpc DeployStoredTriggerActionSetReplace(StringMessage) returns (TriggerActionSet) {} // Adds a set of additional TriggerActions, returns a set of all Triggeractions registered afterwards
rpc DeployStoredTriggerActionSetAdd(StringMessage) returns (TriggerActionSet) {} // Replaces registered TriggerActions with given set, returns a set ONLY OF ADDED TriggerActions (with assigned IDs)
// DB backup&restore
rpc DBBackup(StringMessage) returns(Empty) {}
rpc DBRestore(StringMessage) returns(Empty) {}
rpc ListStoredHIDScripts(Empty) returns (StringMessageArray) {}
rpc ListStoredBashScripts(Empty) returns (StringMessageArray) {}
rpc ListStoredDBBackups(Empty) returns (StringMessageArray) {}
}
/* Bluetooth */
message BluetoothAgentSettings {
string pin = 1;

View File

@ -4,6 +4,7 @@ import (
"errors"
"github.com/dgraph-io/badger"
_ "github.com/dgraph-io/badger"
"os"
"strings"
)
@ -33,6 +34,7 @@ func (s *Store) Open() (err error) {
badgerOpts.Dir = s.Path
badgerOpts.ValueDir = s.Path
badgerOpts.SyncWrites = true
badgerOpts.ManagedTxns = true //needed for DropAll()
s.Db,err = badger.Open(badgerOpts)
if s.serializer == nil {
s.serializer = NewSerializerProtobuf(false)
@ -44,6 +46,30 @@ func (s *Store) Close() {
s.Db.Close()
}
// ToDo: Backup and restore could be synchronized to avoid concurrent transactions
func (s *Store) Backup(filePath string) (err error) {
f, err := os.OpenFile(filePath, os.O_WRONLY|os.O_CREATE|os.O_TRUNC, 0664)
if err != nil {
return err
}
defer f.Close()
_,err = s.Db.Backup(f,0)
return
}
func (s *Store) Restore(filePath string) (err error) {
f, err := os.Open(filePath)
if err != nil {
return err
}
defer f.Close()
// DB should be cleared first
err = s.Db.DropAll()
if err != nil { return }
err = s.Db.Load(f)
return
}
func (s *Store) Put(key string, value interface{}, allowOverwrite bool) (err error) {
// ToDo: Remove race condition (existence check and value set have to be merged into a single transaction)
if !allowOverwrite && s.Exists(key) {

View File

@ -7,4 +7,5 @@ const (
PATH_BASH_SCRIPTS = PATH_ROOT + "/scripts"
PATH_HID_SCRIPTS = PATH_ROOT + "/HIDScripts"
PATH_DATA_STORE = PATH_ROOT + "/store"
PATH_DATA_STORE_BACKUP = PATH_ROOT + "/db"
)

View File

@ -15,6 +15,7 @@ import (
"io"
"log"
"net"
"path/filepath"
"net/http"
"path"
@ -51,6 +52,38 @@ type server struct {
listenAddrWeb string
}
func (s *server) DBBackup(ctx context.Context, filename *pb.StringMessage) (e *pb.Empty, err error) {
e = &pb.Empty{}
fname := filename.Msg
ext := filepath.Ext(fname)
if lext := strings.ToLower(ext); lext != ".db" {
fname = fname + ".db"
}
err = s.rootSvc.SubSysDataStore.Backup(PATH_DATA_STORE_BACKUP + "/" + fname)
return
}
func (s *server) DBRestore(ctx context.Context, filename *pb.StringMessage) (e *pb.Empty, err error) {
e = &pb.Empty{}
fname := filename.Msg
ext := filepath.Ext(fname)
if lext := strings.ToLower(ext); lext != ".db" {
fname = fname + ".db"
}
err = s.rootSvc.SubSysDataStore.Restore(PATH_DATA_STORE_BACKUP + "/" + fname)
return
}
func (s *server) ListStoredDBBackups(context.Context, *pb.Empty) (*pb.StringMessageArray, error) {
scripts,err := ListFilesOfFolder(PATH_DATA_STORE_BACKUP, ".db")
if err != nil { return nil,err }
return &pb.StringMessageArray{MsgArray:scripts}, nil
}
func (s *server) GetBluetoothAgentSettings(ctx context.Context, e *pb.Empty) (as *pb.BluetoothAgentSettings, err error) {
pin,err := s.rootSvc.SubSysBluetooth.GetPIN()
if err != nil { return nil,err }