1#!/usr/bin/awk -f
2# Generate sorted list of directories.  The sorting is stable but with
3# dependencies between directories resolved by moving dependees in front.
4# Copyright (C) 1998-2022 Free Software Foundation, Inc.
5
6BEGIN {
7  cnt = split(subdirs, all) + 1
8  dnt = 0
9}
10
11# Let input files have comments.
12{ sub(/[ 	]*#.*$/, "") }
13NF == 0 { next }
14
15{
16  subdir = type = FILENAME;
17  sub(/^.*\//, "", type);
18  sub(/\/[^/]+$/, "", subdir);
19  sub(/^.*\//, "", subdir);
20  thisdir = "";
21}
22
23type == "Depend" && NF == 1 {
24  from[dnt] = subdir;
25  to[dnt] = $1;
26  ++dnt;
27  next
28}
29
30type == "Subdirs" && NF == 1 { thisdir = $1 }
31
32type == "Subdirs" && NF == 2 && $1 == "first" {
33  thisdir = $2;
34  # Make the first dir in the list depend on this one.
35  from[dnt] = all[1];
36  to[dnt] = thisdir;
37  ++dnt;
38}
39
40type == "Subdirs" && NF == 2 && $1 == "inhibit" {
41  inhibit[$2] = subdir;
42  next
43}
44
45type == "Subdirs" && thisdir {
46  all[cnt++] = thisdir;
47
48  this_srcdir = srcpfx thisdir
49  if (system("test -d " this_srcdir) != 0) {
50    print FILENAME ":" FNR ":", "cannot find", this_srcdir > "/dev/stderr";
51    exit 2
52  }
53  file = this_srcdir "/Depend";
54  if (system("test -f " file) == 0) {
55    ARGV[ARGC++] = file;
56    # Emit a dependency on the implicitly-read file.
57    if (srcpfx)
58      sub(/^\.\.\//, "", file);
59    if (file !~ /^\/.*$/)
60      file = "$(..)" file;
61    print "$(common-objpfx)sysd-sorted:", "$(wildcard", file ")";
62  }
63  next
64}
65
66{
67  print FILENAME ":" FNR ":", "what type of file is this?" > "/dev/stderr";
68  exit 2
69}
70
71END {
72  do {
73    moved = 0
74    for (i = 0; i < dnt; ++i) {
75      for (j = 1; j < cnt; ++j) {
76	if (all[j] == from[i]) {
77	  for (k = j + 1; k < cnt; ++k) {
78	    if (all[k] == to[i]) {
79	      break;
80	    }
81	  }
82	  if (k < cnt) {
83	    for (l = k - 1; l >= j; --l) {
84	      all[l + 1] = all[l]
85	    }
86	    all[j] = to[i]
87	    break;
88	  }
89	}
90      }
91      if (j < cnt) {
92	moved = 1
93	break
94      }
95    }
96  } while (moved);
97
98  # Make sure we list "elf" last.
99  saw_elf = 0;
100  printf "sorted-subdirs :=";
101  for (i = 1; i < cnt; ++i) {
102    if (all[i] in inhibit)
103      continue;
104    if (all[i] == "elf")
105      saw_elf = 1;
106    else
107      printf " %s", all[i];
108  }
109  printf "%s\n", saw_elf ? " elf" : "";
110
111  print "sysd-sorted-done := t"
112}
113