Implement command line option and configuration handling
This commit is contained in:
parent
3baa75fd8c
commit
a634cc5679
2
.gitignore
vendored
2
.gitignore
vendored
|
@ -1 +1,3 @@
|
||||||
*~
|
*~
|
||||||
|
__pycache__
|
||||||
|
archive
|
||||||
|
|
74
README.md
74
README.md
|
@ -1 +1,75 @@
|
||||||
# Sysadmin Tools
|
# Sysadmin Tools
|
||||||
|
|
||||||
|
## Steps
|
||||||
|
|
||||||
|
### Make kernel source
|
||||||
|
|
||||||
|
- emerge -1
|
||||||
|
- store kernel source
|
||||||
|
- emerge unmerge
|
||||||
|
|
||||||
|
```bash
|
||||||
|
ktool mksrc
|
||||||
|
```
|
||||||
|
|
||||||
|
### Prepare kernel source
|
||||||
|
|
||||||
|
- load kernel source
|
||||||
|
- add .config
|
||||||
|
- make prepare
|
||||||
|
- store prepared kernel source
|
||||||
|
|
||||||
|
```bash
|
||||||
|
ktool prepare
|
||||||
|
```
|
||||||
|
|
||||||
|
### Build kernel source package
|
||||||
|
|
||||||
|
- emerge -1b prepared kernel source package
|
||||||
|
|
||||||
|
```bash
|
||||||
|
ktool emergesrc
|
||||||
|
```
|
||||||
|
|
||||||
|
### Build kernel & modules
|
||||||
|
|
||||||
|
- make bzimage modules
|
||||||
|
- store built kernel source
|
||||||
|
- store built kernel
|
||||||
|
- make modules_install
|
||||||
|
- store built modules
|
||||||
|
|
||||||
|
```bash
|
||||||
|
ktool build
|
||||||
|
```
|
||||||
|
|
||||||
|
### Build initrd
|
||||||
|
|
||||||
|
- load built modules
|
||||||
|
- build initrd
|
||||||
|
- store initrd
|
||||||
|
|
||||||
|
```bash
|
||||||
|
ktool initrd
|
||||||
|
```
|
||||||
|
|
||||||
|
### Build ucodes
|
||||||
|
|
||||||
|
- build ucodes
|
||||||
|
- store ucodes
|
||||||
|
|
||||||
|
```bash
|
||||||
|
ktool mkucodes
|
||||||
|
```
|
||||||
|
|
||||||
|
### Install kernel
|
||||||
|
|
||||||
|
- load ucodes
|
||||||
|
- load built kernel
|
||||||
|
- load built modules
|
||||||
|
- emerge -1K prepared kernel source package
|
||||||
|
- grub-mkconfig
|
||||||
|
|
||||||
|
```bash
|
||||||
|
ktool install
|
||||||
|
```
|
||||||
|
|
8
config/00defaults.yaml
Normal file
8
config/00defaults.yaml
Normal file
|
@ -0,0 +1,8 @@
|
||||||
|
# base URL for distribution
|
||||||
|
baseurl: https://apps.karinthy.hu/gentoo/
|
||||||
|
|
||||||
|
# base subdirectory for distribution
|
||||||
|
distdir: distribution
|
||||||
|
|
||||||
|
# kernel series to use (latest or x.y)
|
||||||
|
kernels: latest
|
140
configuration.py
Normal file
140
configuration.py
Normal file
|
@ -0,0 +1,140 @@
|
||||||
|
# -*- coding: UTF-8 -*-
|
||||||
|
|
||||||
|
import os
|
||||||
|
import sys
|
||||||
|
import getopt
|
||||||
|
from yaml import load, YAMLError
|
||||||
|
try:
|
||||||
|
from yaml import CSafeLoader as SafeLoader
|
||||||
|
except ImportError:
|
||||||
|
from yaml import SafeLoader
|
||||||
|
from pathlib import Path
|
||||||
|
|
||||||
|
class Config():
|
||||||
|
def __init__(self, scriptname, progver, commands):
|
||||||
|
scriptname = os.path.realpath(scriptname)
|
||||||
|
self.basedir = os.path.dirname(scriptname)
|
||||||
|
self.progname = os.path.basename(scriptname)
|
||||||
|
self.progver = progver
|
||||||
|
self.commands = commands
|
||||||
|
# options
|
||||||
|
self.help = False
|
||||||
|
self.version = False
|
||||||
|
self.verbose = False
|
||||||
|
self.config = "config"
|
||||||
|
self.params = {}
|
||||||
|
# command
|
||||||
|
self.cmd = None
|
||||||
|
# config params
|
||||||
|
self.config_params = {}
|
||||||
|
|
||||||
|
def usage(self, exitcode):
|
||||||
|
usage = """Usage: """ + self.progname + """ [<options>] <command> [<options>]
|
||||||
|
|
||||||
|
Commands:
|
||||||
|
"""
|
||||||
|
for cmd, desc in self.commands:
|
||||||
|
usage += " " + cmd + (' ' if len(cmd) >= 31 else ' ' * (31-len(cmd))) + desc + "\n"
|
||||||
|
usage += """
|
||||||
|
Options:
|
||||||
|
-h, --help Print this help
|
||||||
|
-V, --version Print version number
|
||||||
|
-c, --config dir Specify config directory to read [""" + self.config + """]
|
||||||
|
-s, --set key=value Override config parameter key=value
|
||||||
|
-v, --verbose Print verbose messages
|
||||||
|
"""
|
||||||
|
sys.stderr.write(usage)
|
||||||
|
if exitcode is not None:
|
||||||
|
sys.exit(exitcode)
|
||||||
|
|
||||||
|
def parse(self, argv):
|
||||||
|
try:
|
||||||
|
(opt, args) = getopt.gnu_getopt(argv[1:], "hVvc:s:", [
|
||||||
|
"help", "version", "verbose", "config=", "set="
|
||||||
|
])
|
||||||
|
except getopt.GetoptError as e:
|
||||||
|
sys.stderr.write("Error: %s\n" % str(e))
|
||||||
|
self.usage(2)
|
||||||
|
|
||||||
|
for o, a in opt:
|
||||||
|
if o == '-h' or o == "--help":
|
||||||
|
self.help = True
|
||||||
|
elif o == '-V' or o == "--version":
|
||||||
|
self.version = True
|
||||||
|
elif o == '-v' or o == "--verbose":
|
||||||
|
self.verbose = True
|
||||||
|
elif o == '-c' or o == "--config":
|
||||||
|
if (a == ''):
|
||||||
|
sys.stderr.write("Error: option " + o + " requires a non-empty argument\n")
|
||||||
|
self.usage(2)
|
||||||
|
self.config = a
|
||||||
|
elif o == '-s' or o == "--set":
|
||||||
|
parts = a.partition('=')
|
||||||
|
if (parts[1] != '='):
|
||||||
|
sys.stderr.write("Error: option " + o + " requires argument in the format key=value\n")
|
||||||
|
self.usage(2)
|
||||||
|
if (parts[0] == ''):
|
||||||
|
sys.stderr.write("Error: option " + o + " requires argument in the format key=value; key may not be an empty string\n")
|
||||||
|
self.usage(2)
|
||||||
|
self.params[parts[0]] = parts[2]
|
||||||
|
|
||||||
|
if self.version:
|
||||||
|
sys.stdout.write("Version: " + self.progver + "\n")
|
||||||
|
if self.help:
|
||||||
|
self.usage(None)
|
||||||
|
if self.version or self.help:
|
||||||
|
sys.exit(0)
|
||||||
|
|
||||||
|
self.load_config()
|
||||||
|
|
||||||
|
for c in args:
|
||||||
|
if self.cmd != None:
|
||||||
|
sys.stderr.write("Multiple commands specified: " + self.cmd + " vs " + c + "\n")
|
||||||
|
self.usage(2)
|
||||||
|
for cmd, _ in self.commands:
|
||||||
|
if c == cmd:
|
||||||
|
self.cmd = c
|
||||||
|
break
|
||||||
|
if self.cmd == None:
|
||||||
|
sys.stderr.write("Unknown command specified: " + c + "\n")
|
||||||
|
self.usage(2)
|
||||||
|
if self.cmd == None:
|
||||||
|
sys.stderr.write("Missing command\n")
|
||||||
|
self.usage(2)
|
||||||
|
|
||||||
|
for k, v in self.params.items():
|
||||||
|
self.config_params[k] = v
|
||||||
|
if self.verbose:
|
||||||
|
sys.stdout.write("Config parameters:\n")
|
||||||
|
for k, v in self.config_params.items():
|
||||||
|
sys.stdout.write(" " + k + "=" + str(v) + "\n")
|
||||||
|
|
||||||
|
def merge_config(self, src, dest):
|
||||||
|
for key, value in src.items():
|
||||||
|
if isinstance(value, dict):
|
||||||
|
node = dest.setdefault(key, {})
|
||||||
|
self.merge_config(value, node)
|
||||||
|
else:
|
||||||
|
dest[key] = value
|
||||||
|
return dest
|
||||||
|
|
||||||
|
def parse_file(self, filepath):
|
||||||
|
try:
|
||||||
|
obj = load(open(filepath, 'r'), SafeLoader)
|
||||||
|
self.merge_config(obj, self.config_params)
|
||||||
|
except YAMLError as exc:
|
||||||
|
sys.stdout.write("Error: reading configuration file failed: %s" % (exc))
|
||||||
|
|
||||||
|
def load_config(self):
|
||||||
|
configdir = self.config if self.config.startswith('/') else self.basedir + '/' + self.config
|
||||||
|
if self.verbose:
|
||||||
|
sys.stdout.write("Reading config directory " + configdir + "\n")
|
||||||
|
if not Path(configdir).is_dir():
|
||||||
|
sys.stderr.write("Warning: config directory " + configdir + " does not exist\n")
|
||||||
|
return
|
||||||
|
with os.scandir(configdir) as it:
|
||||||
|
for entry in it:
|
||||||
|
if not entry.name.startswith('.') and (entry.name.endswith('.yml') or entry.name.endswith('.yaml')) and entry.is_file():
|
||||||
|
if self.verbose:
|
||||||
|
sys.stdout.write("Parsing config file " + entry.path + "\n")
|
||||||
|
self.parse_file(entry.path)
|
19
ktool
Executable file
19
ktool
Executable file
|
@ -0,0 +1,19 @@
|
||||||
|
#!/usr/bin/env python3
|
||||||
|
# -*- coding: UTF-8 -*-
|
||||||
|
|
||||||
|
import os
|
||||||
|
import sys
|
||||||
|
|
||||||
|
import progver
|
||||||
|
from configuration import Config
|
||||||
|
|
||||||
|
config = Config(__file__, progver.VERSION, [
|
||||||
|
['mksrc', 'Make kernel source'],
|
||||||
|
['prepare', 'Prepare kernel source'],
|
||||||
|
['emergesrc', 'Build kernel source package'],
|
||||||
|
['build', 'Build kernel & modules'],
|
||||||
|
['initrd', 'Build initrd'],
|
||||||
|
['mkucodes', 'Build ucodes'],
|
||||||
|
['install', 'Install kernel']
|
||||||
|
])
|
||||||
|
config.parse(sys.argv)
|
6
progver.py
Normal file
6
progver.py
Normal file
|
@ -0,0 +1,6 @@
|
||||||
|
# -*- coding: UTF-8 -*-
|
||||||
|
|
||||||
|
import sys
|
||||||
|
|
||||||
|
this = sys.modules[__name__]
|
||||||
|
this.VERSION = "0.01"
|
Loading…
Reference in a new issue