github.com/hugh712/snapd@v0.0.0-20200910133618-1a99902bd583/overlord/configstate/configcore/picfg.go (about) 1 // -*- Mode: Go; indent-tabs-mode: t -*- 2 3 /* 4 * Copyright (C) 2017 Canonical Ltd 5 * 6 * This program is free software: you can redistribute it and/or modify 7 * it under the terms of the GNU General Public License version 3 as 8 * published by the Free Software Foundation. 9 * 10 * This program is distributed in the hope that it will be useful, 11 * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 * GNU General Public License for more details. 14 * 15 * You should have received a copy of the GNU General Public License 16 * along with this program. If not, see <http://www.gnu.org/licenses/>. 17 * 18 */ 19 20 package configcore 21 22 import ( 23 "fmt" 24 "os" 25 "path/filepath" 26 "strings" 27 28 "github.com/snapcore/snapd/dirs" 29 "github.com/snapcore/snapd/osutil" 30 "github.com/snapcore/snapd/overlord/configstate/config" 31 ) 32 33 // valid pi config keys 34 var piConfigKeys = map[string]bool{ 35 "disable_overscan": true, 36 "force_turbo": true, 37 "framebuffer_width": true, 38 "framebuffer_height": true, 39 "framebuffer_depth": true, 40 "framebuffer_ignore_alpha": true, 41 "overscan_left": true, 42 "overscan_right": true, 43 "overscan_top": true, 44 "overscan_bottom": true, 45 "overscan_scale": true, 46 "display_rotate": true, 47 "hdmi_group": true, 48 "hdmi_mode": true, 49 "hdmi_drive": true, 50 "avoid_warnings": true, 51 "gpu_mem_256": true, 52 "gpu_mem_512": true, 53 "gpu_mem": true, 54 "sdtv_aspect": true, 55 "config_hdmi_boost": true, 56 "hdmi_force_hotplug": true, 57 "start_x": true, 58 } 59 60 func init() { 61 // add supported config keys 62 for k := range piConfigKeys { 63 s := fmt.Sprintf("core.pi-config.%s", strings.Replace(k, "_", "-", -1)) 64 supportedConfigurations[s] = true 65 } 66 } 67 68 func updatePiConfig(path string, config map[string]string) error { 69 f, err := os.Open(path) 70 if err != nil { 71 return err 72 } 73 defer f.Close() 74 75 toWrite, err := updateKeyValueStream(f, piConfigKeys, config) 76 if err != nil { 77 return err 78 } 79 80 if toWrite != nil { 81 s := strings.Join(toWrite, "\n") 82 // ensure we have a final newline in the file 83 s += "\n" 84 return osutil.AtomicWriteFile(path, []byte(s), 0644, 0) 85 } 86 87 return nil 88 } 89 90 func piConfigFile(opts *fsOnlyContext) string { 91 rootDir := dirs.GlobalRootDir 92 if opts != nil { 93 rootDir = opts.RootDir 94 } 95 return filepath.Join(rootDir, "/boot/uboot/config.txt") 96 } 97 98 func handlePiConfiguration(tr config.ConfGetter, opts *fsOnlyContext) error { 99 if osutil.FileExists(piConfigFile(opts)) { 100 // snapctl can actually give us the whole dict in 101 // JSON, in a single call; use that instead of this. 102 config := map[string]string{} 103 for key := range piConfigKeys { 104 output, err := coreCfg(tr, fmt.Sprintf("pi-config.%s", strings.Replace(key, "_", "-", -1))) 105 if err != nil { 106 return err 107 } 108 config[key] = output 109 } 110 if err := updatePiConfig(piConfigFile(opts), config); err != nil { 111 return err 112 } 113 } 114 return nil 115 }