[coreboot-gerrit] New patch to review for coreboot: MAINTAINERS: Add script to test database and find maintainers
Stefan Reinauer (stefan.reinauer@coreboot.org)
gerrit at coreboot.org
Wed Oct 21 22:17:32 CEST 2015
Stefan Reinauer (stefan.reinauer at coreboot.org) just uploaded a new patch set to gerrit, which you can find at http://review.coreboot.org/12119
-gerrit
commit 65ed94a40bd6d59a8d166cd2cb22aabe3789c7fd
Author: Stefan Reinauer <reinauer at chromium.org>
Date: Wed Oct 21 13:12:51 2015 -0700
MAINTAINERS: Add script to test database and find maintainers
This utility should make it easier to complete and maintain
the database of coreboot subsystem maintainers (MAINTAINERS
file)
This will need a bit of tender love and care to print information
in an easily machine readable output for the build system, but its
a first start to query the maintainers database.
Build with:
$ go build util/scripts/maintainers.go
Find a maintainer for a set of files with:
$ ./maintainers Makefile Makefile.inc
Makefile is in subsystem BUILD SYSTEM
Maintainers: [Patrick Georgi <patrick at georgi-clan.de>]
Makefile.inc is in subsystem BUILD SYSTEM
Maintainers: [Patrick Georgi <patrick at georgi-clan.de>]
Check the maintainer database with:
$ ./maintainers
.gitignore has no subsystem defined in MAINTAINERS
.gitmodules has no subsystem defined in MAINTAINERS
.gitreview has no subsystem defined in MAINTAINERS
3rdparty/arm-trusted-firmware has no subsystem defined in MAINTAINERS
3rdparty/blobs has no subsystem defined in MAINTAINERS
3rdparty/vboot has no subsystem defined in MAINTAINERS
COPYING has no subsystem defined in MAINTAINERS
Documentation/AMD-S3.txt has no subsystem defined in MAINTAINERS
Documentation/CorebootBuildingGuide.tex has no subsystem defined in MAINTAINERS
Documentation/Doxyfile.coreboot has no subsystem defined in MAINTAINERS
[..]
Change-Id: I49c43911971152b0e4d626ccdeb33c088e362695
Signed-off-by: Stefan Reinauer <stefan.reinauer at coreboot.org>
---
util/scripts/maintainers.go | 235 ++++++++++++++++++++++++++++++++++++++++++++
1 file changed, 235 insertions(+)
diff --git a/util/scripts/maintainers.go b/util/scripts/maintainers.go
new file mode 100644
index 0000000..c83b091
--- /dev/null
+++ b/util/scripts/maintainers.go
@@ -0,0 +1,235 @@
+/*
+ * Copyright 2015 Google Inc.
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; version 2 of the License.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ */
+
+package main
+
+import (
+ "fmt"
+ "os"
+ "bufio"
+ "os/exec"
+ "path/filepath"
+)
+
+func get_git_files() ([]string) {
+ /* Read in list of all files in the git repository */
+ cmd := exec.Command("git","ls-files")
+ out, err := cmd.StdoutPipe()
+ if err != nil {
+ panic(err)
+ }
+ cmd.Start()
+
+ var files []string
+ r := bufio.NewScanner(out)
+ for r.Scan() {
+ /* Cut out leading tab */
+ files = append(files, r.Text())
+ }
+
+ return files
+}
+
+func get_maintainers() ([]string) {
+ /* Read in all maintainers */
+ file, err := os.Open("MAINTAINERS")
+ if err != nil {
+ panic(err)
+ }
+ defer file.Close()
+
+ var maintainers []string
+ keep := false
+ s := bufio.NewScanner(file)
+ for s.Scan() {
+ /* Are we in the "data" section and have a non-empty line? */
+ if keep && s.Text() != "" {
+ maintainers = append(maintainers, s.Text())
+ }
+ /* Skip everything before the delimiter */
+ if s.Text() == "\t\t-----------------------------------" {
+ keep = true
+ }
+ }
+
+ return maintainers
+}
+
+type subsystem struct {
+ name string
+ maintainer []string
+ file []string
+}
+
+var subsystems []subsystem
+
+func build_maintainers(maintainers []string) {
+ numsub := -1
+ for _, line := range maintainers {
+ if line[1] != ':' {
+ /* Create new subsystem entry */
+ numsub++
+ var tmp subsystem
+ tmp.name = line
+ subsystems = append(subsystems, tmp)
+ } else {
+ switch line[0] {
+ case 'R':
+ case 'M': {
+ /* Add subsystem maintainer */
+ subsystems[numsub].maintainer =
+ append(subsystems[numsub].maintainer,
+ line[3:len(line)])
+ break
+ }
+ case 'S': {
+ break
+ }
+ case 'L': {
+ break
+ }
+ case 'T': {
+ break
+ }
+ case 'F': {
+ // add files
+ subsystems[numsub].file =
+ append(subsystems[numsub].file,
+ line[3:len(line)])
+ break
+ }
+ default: {
+ fmt.Println("No such specifier: ", line)
+ break
+ }
+ }
+ }
+ }
+}
+
+func print_maintainers() {
+ for _, subsystem := range subsystems {
+ fmt.Println(subsystem.name)
+ fmt.Println(" ", subsystem.maintainer)
+ fmt.Println(" ", subsystem.file)
+ }
+}
+
+func match_file(fname string, files []string) (bool) {
+ matched := false
+ var err error
+ for _, file := range files {
+ /* Direct match */
+ matched, err = filepath.Match(file, fname)
+ if err != nil {
+ panic(err)
+ }
+ if matched {
+ break
+ }
+
+ // If file doesn't end in / skip
+ if file[len(file)-1] != '/' {
+ continue
+ }
+ file += "*"
+
+ /* Maximum tree depth, as calculated by
+ * $(( `git ls-files | tr -d "[a-z][A-Z][0-9]\-\_\." | \
+ * sort -u | tail -1 | wc -c` - 1 ))
+ */
+ max_depth := 11
+ for i := 0; i < max_depth; i++ {
+ matched, err = filepath.Match(file, fname)
+ if err != nil {
+ panic(err)
+ }
+ if matched {
+ break;
+ }
+
+ /* Subdirectory match */
+ file += "/*"
+ }
+ if matched {
+ break
+ }
+ }
+ return matched
+}
+
+func find_maintainer(fname string) {
+ has_subsystem := false
+ for _, subsystem := range subsystems {
+ if match_file(fname, subsystem.file) && subsystem.name != "THE REST" {
+ fmt.Println(fname, "is in subsystem",
+ subsystem.name)
+ fmt.Println("Maintainers: ", subsystem.maintainer)
+ has_subsystem = true
+ break
+ }
+ }
+ if has_subsystem == false {
+ fmt.Println(fname, "has no subsystem defined in MAINTAINERS")
+ }
+}
+
+func find_unmaintained(fname string) {
+ has_subsystem := false
+ for _, subsystem := range subsystems {
+ if match_file(fname, subsystem.file) && subsystem.name != "THE REST" {
+ fmt.Println(fname, "is in subsystem",
+ subsystem.name)
+ has_subsystem = true
+ break
+ }
+ }
+ if has_subsystem == false {
+ fmt.Println(fname, "has no subsystem defined in MAINTAINERS")
+ }
+}
+
+func main() {
+ var files []string
+ var maint bool
+ var debug bool
+
+ args := os.Args[1:]
+ if len(args) == 0 {
+ /* get the filenames */
+ files=get_git_files()
+ maint = false
+ } else {
+ files=args
+ maint = true
+ }
+ maintainers:=get_maintainers()
+
+ /* build subsystem database */
+ build_maintainers(maintainers)
+
+ if debug {
+ print_maintainers()
+ }
+
+ if maint {
+ /* Find maintainers for each file */
+ for _, file := range files {
+ find_maintainer(file)
+ }
+ } else {
+ for _, file := range files {
+ find_unmaintained(file)
+ }
+ }
+}
More information about the coreboot-gerrit
mailing list