Changeset 8565a42 in mainline for tools/config.py


Ignore:
Timestamp:
2018-03-02T20:34:50Z (7 years ago)
Author:
GitHub <noreply@…>
Branches:
lfn, master, serial, ticket/834-toolchain-update, topic/msim-upgrade, topic/simplify-dev-export
Children:
a1a81f69, d5e5fd1
Parents:
3061bc1 (diff), 34e1206 (diff)
Note: this is a merge changeset, the changes displayed below correspond to the merge itself.
Use the (diff) links above to see all the changes relative to each parent.
git-author:
Jiří Zárevúcky <zarevucky.jiri@…> (2018-03-02 20:34:50)
git-committer:
GitHub <noreply@…> (2018-03-02 20:34:50)
Message:

Remove all trailing whitespace, everywhere.

See individual commit messages for details.

File:
1 edited

Legend:

Unmodified
Added
Removed
  • tools/config.py

    r3061bc1 r8565a42  
    4949def read_config(fname, config):
    5050        "Read saved values from last configuration run or a preset file"
    51        
     51
    5252        inf = open(fname, 'r')
    53        
     53
    5454        for line in inf:
    5555                res = re.match(r'^(?:#!# )?([^#]\w*)\s*=\s*(.*?)\s*$', line)
    5656                if res:
    5757                        config[res.group(1)] = res.group(2)
    58        
     58
    5959        inf.close()
    6060
    6161def check_condition(text, config, rules):
    6262        "Check that the condition specified on input line is True (only CNF and DNF is supported)"
    63        
     63
    6464        ctype = 'cnf'
    65        
     65
    6666        if (')|' in text) or ('|(' in text):
    6767                ctype = 'dnf'
    68        
     68
    6969        if ctype == 'cnf':
    7070                conds = text.split('&')
    7171        else:
    7272                conds = text.split('|')
    73        
     73
    7474        for cond in conds:
    7575                if cond.startswith('(') and cond.endswith(')'):
    7676                        cond = cond[1:-1]
    77                
     77
    7878                inside = check_inside(cond, config, ctype)
    79                
     79
    8080                if (ctype == 'cnf') and (not inside):
    8181                        return False
    82                
     82
    8383                if (ctype == 'dnf') and inside:
    8484                        return True
    85        
     85
    8686        if ctype == 'cnf':
    8787                return True
    88        
     88
    8989        return False
    9090
    9191def check_inside(text, config, ctype):
    9292        "Check for condition"
    93        
     93
    9494        if ctype == 'cnf':
    9595                conds = text.split('|')
    9696        else:
    9797                conds = text.split('&')
    98        
     98
    9999        for cond in conds:
    100100                res = re.match(r'^(.*?)(!?=)(.*)$', cond)
    101101                if not res:
    102102                        raise RuntimeError("Invalid condition: %s" % cond)
    103                
     103
    104104                condname = res.group(1)
    105105                oper = res.group(2)
    106106                condval = res.group(3)
    107                
     107
    108108                if not condname in config:
    109109                        varval = ''
     
    112112                        if (varval == '*'):
    113113                                varval = 'y'
    114                
     114
    115115                if ctype == 'cnf':
    116116                        if (oper == '=') and (condval == varval):
    117117                                return True
    118                
     118
    119119                        if (oper == '!=') and (condval != varval):
    120120                                return True
     
    122122                        if (oper == '=') and (condval != varval):
    123123                                return False
    124                        
     124
    125125                        if (oper == '!=') and (condval == varval):
    126126                                return False
    127        
     127
    128128        if ctype == 'cnf':
    129129                return False
    130        
     130
    131131        return True
    132132
    133133def parse_rules(fname, rules):
    134134        "Parse rules file"
    135        
     135
    136136        inf = open(fname, 'r')
    137        
     137
    138138        name = ''
    139139        choices = []
    140        
     140
    141141        for line in inf:
    142                
     142
    143143                if line.startswith('!'):
    144144                        # Ask a question
    145145                        res = re.search(r'!\s*(?:\[(.*?)\])?\s*([^\s]+)\s*\((.*)\)\s*$', line)
    146                        
     146
    147147                        if not res:
    148148                                raise RuntimeError("Weird line: %s" % line)
    149                        
     149
    150150                        cond = res.group(1)
    151151                        varname = res.group(2)
    152152                        vartype = res.group(3)
    153                        
     153
    154154                        rules.append((varname, vartype, name, choices, cond))
    155155                        name = ''
    156156                        choices = []
    157157                        continue
    158                
     158
    159159                if line.startswith('@'):
    160160                        # Add new line into the 'choices' array
    161161                        res = re.match(r'@\s*(?:\[(.*?)\])?\s*"(.*?)"\s*(.*)$', line)
    162                        
     162
    163163                        if not res:
    164164                                raise RuntimeError("Bad line: %s" % line)
    165                        
     165
    166166                        choices.append((res.group(2), res.group(3)))
    167167                        continue
    168                
     168
    169169                if line.startswith('%'):
    170170                        # Name of the option
    171171                        name = line[1:].strip()
    172172                        continue
    173                
     173
    174174                if line.startswith('#') or (line == '\n'):
    175175                        # Comment or empty line
    176176                        continue
    177                
    178                
     177
     178
    179179                raise RuntimeError("Unknown syntax: %s" % line)
    180        
     180
    181181        inf.close()
    182182
    183183def yes_no(default):
    184184        "Return '*' if yes, ' ' if no"
    185        
     185
    186186        if default == 'y':
    187187                return '*'
    188        
     188
    189189        return ' '
    190190
    191191def subchoice(screen, name, choices, default):
    192192        "Return choice of choices"
    193        
     193
    194194        maxkey = 0
    195195        for key, val in choices:
     
    197197                if (length > maxkey):
    198198                        maxkey = length
    199        
     199
    200200        options = []
    201201        position = None
     
    204204                if (default) and (key == default):
    205205                        position = cnt
    206                
     206
    207207                options.append(" %-*s  %s " % (maxkey, key, val))
    208208                cnt += 1
    209        
     209
    210210        (button, value) = xtui.choice_window(screen, name, 'Choose value', options, position)
    211        
     211
    212212        if button == 'cancel':
    213213                return None
    214        
     214
    215215        return choices[value][0]
    216216
     
    228228def infer_verify_choices(config, rules):
    229229        "Infer and verify configuration values."
    230        
     230
    231231        for rule in rules:
    232232                varname, vartype, name, choices, cond = rule
    233                
     233
    234234                if cond and (not check_condition(cond, config, rules)):
    235235                        continue
    236                
     236
    237237                if not varname in config:
    238238                        value = None
    239239                else:
    240240                        value = config[varname]
    241                
     241
    242242                if not validate_rule_value(rule, value):
    243243                        value = None
    244                
     244
    245245                default = get_default_rule(rule)
    246                
     246
    247247                #
    248248                # If we don't have a value but we do have
     
    252252                        value = default
    253253                        config[varname] = default
    254                
     254
    255255                if not varname in config:
    256256                        return False
    257        
     257
    258258        return True
    259259
     
    275275        if start_index >= len(rules):
    276276                return True
    277        
     277
    278278        varname, vartype, name, choices, cond = rules[start_index]
    279279
     
    282282                if not check_condition(cond, config, rules):
    283283                        return random_choices(config, rules, start_index + 1)
    284        
     284
    285285        # Remember previous choices for backtracking
    286286        yes_no = 0
    287287        choices_indexes = range(0, len(choices))
    288288        random.shuffle(choices_indexes)
    289        
     289
    290290        # Remember current configuration value
    291291        old_value = None
     
    294294        except KeyError:
    295295                old_value = None
    296        
     296
    297297        # For yes/no choices, we ran the loop at most 2 times, for select
    298298        # choices as many times as there are options.
     
    320320                else:
    321321                        raise RuntimeError("Unknown variable type: %s" % vartype)
    322        
     322
    323323                config[varname] = value
    324                
     324
    325325                ok = random_choices(config, rules, start_index + 1)
    326326                if ok:
    327327                        return True
    328                
     328
    329329                try_counter = try_counter + 1
    330        
     330
    331331        # Restore the old value and backtrack
    332332        # (need to delete to prevent "ghost" variables that do not exist under
     
    335335        if old_value is None:
    336336                del config[varname]
    337        
     337
    338338        return random_choices(config, rules, start_index + 1)
    339        
     339
    340340
    341341## Get default value from a rule.
    342342def get_default_rule(rule):
    343343        varname, vartype, name, choices, cond = rule
    344        
     344
    345345        default = None
    346        
     346
    347347        if vartype == 'choice':
    348348                # If there is just one option, use it
     
    359359        else:
    360360                raise RuntimeError("Unknown variable type: %s" % vartype)
    361        
     361
    362362        return default
    363363
     
    371371def get_rule_option(rule, value):
    372372        varname, vartype, name, choices, cond = rule
    373        
     373
    374374        option = None
    375        
     375
    376376        if vartype == 'choice':
    377377                # If there is just one option, don't ask
     
    391391        else:
    392392                raise RuntimeError("Unknown variable type: %s" % vartype)
    393        
     393
    394394        return option
    395395
     
    403403def validate_rule_value(rule, value):
    404404        varname, vartype, name, choices, cond = rule
    405        
     405
    406406        if value == None:
    407407                return True
    408        
     408
    409409        if vartype == 'choice':
    410410                if not value in [choice[0] for choice in choices]:
     
    424424        else:
    425425                raise RuntimeError("Unknown variable type: %s" % vartype)
    426        
     426
    427427        return True
    428428
    429429def preprocess_config(config, rules):
    430430        "Preprocess configuration"
    431        
     431
    432432        varname_mode = 'CONFIG_BFB_MODE'
    433433        varname_width = 'CONFIG_BFB_WIDTH'
    434434        varname_height = 'CONFIG_BFB_HEIGHT'
    435        
     435
    436436        if varname_mode in config:
    437437                mode = config[varname_mode].partition('x')
    438                
     438
    439439                config[varname_width] = mode[0]
    440440                rules.append((varname_width, 'choice', 'Default framebuffer width', None, None))
    441                
     441
    442442                config[varname_height] = mode[2]
    443443                rules.append((varname_height, 'choice', 'Default framebuffer height', None, None))
     
    445445def create_output(mkname, mcname, config, rules):
    446446        "Create output configuration"
    447        
     447
    448448        varname_strip = 'CONFIG_STRIP_REVISION_INFO'
    449449        strip_rev_info = (varname_strip in config) and (config[varname_strip] == 'y')
    450        
     450
    451451        if strip_rev_info:
    452452                timestamp_unix = int(0)
     
    454454                # TODO: Use commit timestamp instead of build time.
    455455                timestamp_unix = int(time.time())
    456        
     456
    457457        timestamp = time.strftime("%Y-%m-%d %H:%M:%S", time.localtime(timestamp_unix))
    458        
     458
    459459        sys.stderr.write("Fetching current revision identifier ... ")
    460        
     460
    461461        try:
    462462                version = subprocess.Popen(['git', 'log', '-1', '--pretty=%h'], stdout = subprocess.PIPE).communicate()[0].decode().strip()
     
    465465                version = None
    466466                sys.stderr.write("failed\n")
    467        
     467
    468468        if (not strip_rev_info) and (version is not None):
    469469                revision = version
    470470        else:
    471471                revision = None
    472        
     472
    473473        outmk = open(mkname, 'w')
    474474        outmc = open(mcname, 'w')
    475        
     475
    476476        outmk.write('#########################################\n')
    477477        outmk.write('## AUTO-GENERATED FILE, DO NOT EDIT!!! ##\n')
    478478        outmk.write('## Generated by: tools/config.py       ##\n')
    479479        outmk.write('#########################################\n\n')
    480        
     480
    481481        outmc.write('/***************************************\n')
    482482        outmc.write(' * AUTO-GENERATED FILE, DO NOT EDIT!!! *\n')
    483483        outmc.write(' * Generated by: tools/config.py       *\n')
    484484        outmc.write(' ***************************************/\n\n')
    485        
     485
    486486        defs = 'CONFIG_DEFS ='
    487        
     487
    488488        for varname, vartype, name, choices, cond in rules:
    489489                if cond and (not check_condition(cond, config, rules)):
    490490                        continue
    491                
     491
    492492                if not varname in config:
    493493                        value = ''
     
    496496                        if (value == '*'):
    497497                                value = 'y'
    498                
     498
    499499                outmk.write('# %s\n%s = %s\n\n' % (name, varname, value))
    500                
     500
    501501                if vartype in ["y", "n", "y/n", "n/y"]:
    502502                        if value == "y":
     
    506506                        outmc.write('/* %s */\n#define %s %s\n#define %s_%s\n\n' % (name, varname, value, varname, value))
    507507                        defs += ' -D%s=%s -D%s_%s' % (varname, value, varname, value)
    508        
     508
    509509        if revision is not None:
    510510                outmk.write('REVISION = %s\n' % revision)
    511511                outmc.write('#define REVISION %s\n' % revision)
    512512                defs += ' "-DREVISION=%s"' % revision
    513        
     513
    514514        outmk.write('TIMESTAMP_UNIX = %d\n' % timestamp_unix)
    515515        outmc.write('#define TIMESTAMP_UNIX %d\n' % timestamp_unix)
    516516        defs += ' "-DTIMESTAMP_UNIX=%d"\n' % timestamp_unix
    517        
     517
    518518        outmk.write('TIMESTAMP = %s\n' % timestamp)
    519519        outmc.write('#define TIMESTAMP %s\n' % timestamp)
    520520        defs += ' "-DTIMESTAMP=%s"\n' % timestamp
    521        
     521
    522522        outmk.write(defs)
    523        
     523
    524524        outmk.close()
    525525        outmc.close()
     
    536536        opt2path = {}
    537537        cnt = 0
    538        
     538
    539539        # Look for profiles
    540540        for name in sorted_dir(root):
    541541                path = os.path.join(root, name)
    542542                canon = os.path.join(path, fname)
    543                
     543
    544544                if os.path.isdir(path) and os.path.exists(canon) and os.path.isfile(canon):
    545545                        subprofile = False
    546                        
     546
    547547                        # Look for subprofiles
    548548                        for subname in sorted_dir(path):
    549549                                subpath = os.path.join(path, subname)
    550550                                subcanon = os.path.join(subpath, fname)
    551                                
     551
    552552                                if os.path.isdir(subpath) and os.path.exists(subcanon) and os.path.isfile(subcanon):
    553553                                        subprofile = True
     
    555555                                        opt2path[cnt] = [name, subname]
    556556                                        cnt += 1
    557                        
     557
    558558                        if not subprofile:
    559559                                options.append(name)
    560560                                opt2path[cnt] = [name]
    561561                                cnt += 1
    562        
     562
    563563        (button, value) = xtui.choice_window(screen, 'Load preconfigured defaults', 'Choose configuration profile', options, None)
    564        
     564
    565565        if button == 'cancel':
    566566                return None
    567        
     567
    568568        return opt2path[value]
    569569
     
    576576        path = os.path.join(PRESETS_DIR, profile[0], MAKEFILE)
    577577        read_config(path, config)
    578        
     578
    579579        if len(profile) > 1:
    580580                path = os.path.join(PRESETS_DIR, profile[0], profile[1], MAKEFILE)
     
    588588def parse_profile_name(profile_name):
    589589        profile = []
    590        
     590
    591591        head, tail = os.path.split(profile_name)
    592592        if head != '':
    593593                profile.append(head)
    594        
     594
    595595        profile.append(tail)
    596596        return profile
     
    600600        config = {}
    601601        rules = []
    602        
     602
    603603        # Parse rules file
    604604        parse_rules(RULES_FILE, rules)
    605        
     605
    606606        # Input configuration file can be specified on command line
    607607        # otherwise configuration from previous run is used.
     
    611611        elif os.path.exists(MAKEFILE):
    612612                read_config(MAKEFILE, config)
    613        
     613
    614614        # Default mode: check values and regenerate configuration files
    615615        if (len(sys.argv) >= 3) and (sys.argv[2] == 'default'):
     
    618618                        create_output(MAKEFILE, MACROS, config, rules)
    619619                        return 0
    620        
     620
    621621        # Hands-off mode: check values and regenerate configuration files,
    622622        # but no interactive fallback
     
    627627                        sys.stderr.write("Configuration error: No presets specified\n")
    628628                        return 2
    629                
     629
    630630                if (infer_verify_choices(config, rules)):
    631631                        preprocess_config(config, rules)
    632632                        create_output(MAKEFILE, MACROS, config, rules)
    633633                        return 0
    634                
     634
    635635                sys.stderr.write("Configuration error: The presets are ambiguous\n")
    636636                return 1
    637        
     637
    638638        # Check mode: only check configuration
    639639        if (len(sys.argv) >= 3) and (sys.argv[2] == 'check'):
     
    641641                        return 0
    642642                return 1
    643        
     643
    644644        # Random mode
    645645        if (len(sys.argv) == 3) and (sys.argv[2] == 'random'):
     
    653653                preprocess_config(config, rules)
    654654                create_output(MAKEFILE, MACROS, config, rules)
    655                
     655
    656656                return 0
    657        
     657
    658658        screen = xtui.screen_init()
    659659        try:
     
    661661                position = None
    662662                while True:
    663                        
     663
    664664                        # Cancel out all values which have to be deduced
    665665                        for varname, vartype, name, choices, cond in rules:
    666666                                if (vartype == 'y') and (varname in config) and (config[varname] == '*'):
    667667                                        config[varname] = None
    668                        
     668
    669669                        options = []
    670670                        opt2row = {}
    671671                        cnt = 1
    672                        
     672
    673673                        options.append("  --- Load preconfigured defaults ... ")
    674                        
     674
    675675                        for rule in rules:
    676676                                varname, vartype, name, choices, cond = rule
    677                                
     677
    678678                                if cond and (not check_condition(cond, config, rules)):
    679679                                        continue
    680                                
     680
    681681                                if varname == selname:
    682682                                        position = cnt
    683                                
     683
    684684                                if not varname in config:
    685685                                        value = None
    686686                                else:
    687687                                        value = config[varname]
    688                                
     688
    689689                                if not validate_rule_value(rule, value):
    690690                                        value = None
    691                                
     691
    692692                                default = get_default_rule(rule)
    693                                
     693
    694694                                #
    695695                                # If we don't have a value but we do have
     
    699699                                        value = default
    700700                                        config[varname] = default
    701                                
     701
    702702                                option = get_rule_option(rule, value)
    703703                                if option != None:
     
    705705                                else:
    706706                                        continue
    707                                
     707
    708708                                opt2row[cnt] = (varname, vartype, name, choices)
    709                                
     709
    710710                                cnt += 1
    711                        
     711
    712712                        if (position != None) and (position >= len(options)):
    713713                                position = None
    714                        
     714
    715715                        (button, value) = xtui.choice_window(screen, 'HelenOS configuration', 'Choose configuration option', options, position)
    716                        
     716
    717717                        if button == 'cancel':
    718718                                return 'Configuration canceled'
    719                        
     719
    720720                        if button == 'done':
    721721                                if (infer_verify_choices(config, rules)):
     
    724724                                        xtui.error_dialog(screen, 'Error', 'Some options have still undefined values. These options are marked with the "?" sign.')
    725725                                        continue
    726                        
     726
    727727                        if value == 0:
    728728                                profile = choose_profile(PRESETS_DIR, MAKEFILE, screen, config)
     
    731731                                position = 1
    732732                                continue
    733                        
     733
    734734                        position = None
    735735                        if not value in opt2row:
    736736                                raise RuntimeError("Error selecting value: %s" % value)
    737                        
     737
    738738                        (selname, seltype, name, choices) = opt2row[value]
    739                        
     739
    740740                        if not selname in config:
    741741                                value = None
    742742                        else:
    743743                                value = config[selname]
    744                        
     744
    745745                        if seltype == 'choice':
    746746                                config[selname] = subchoice(screen, name, choices, value)
     
    752752        finally:
    753753                xtui.screen_done(screen)
    754        
     754
    755755        preprocess_config(config, rules)
    756756        create_output(MAKEFILE, MACROS, config, rules)
Note: See TracChangeset for help on using the changeset viewer.