Fix for SF bug

https://sourceforge.net/bugs/?func=detailbug&bug_id=126863&group_id=5470
"getopt long option handling broken".  Tossed the excruciating logic in
long_has_args in favor of something obviously correct.
This commit is contained in:
Tim Peters 2000-12-27 08:05:05 +00:00
parent da7bf4e236
commit dd699b62c5
1 changed files with 30 additions and 13 deletions

View File

@ -66,7 +66,7 @@ def getopt(args, shortopts, longopts = []):
else: else:
longopts = list(longopts) longopts = list(longopts)
longopts.sort() longopts.sort()
while args and args[0][:1] == '-' and args[0] != '-': while args and args[0].startswith('-') and args[0] != '-':
if args[0] == '--': if args[0] == '--':
args = args[1:] args = args[1:]
break break
@ -80,9 +80,10 @@ def getopt(args, shortopts, longopts = []):
def do_longs(opts, opt, longopts, args): def do_longs(opts, opt, longopts, args):
try: try:
i = opt.index('=') i = opt.index('=')
opt, optarg = opt[:i], opt[i+1:]
except ValueError: except ValueError:
optarg = None optarg = None
else:
opt, optarg = opt[:i], opt[i+1:]
has_arg, opt = long_has_args(opt, longopts) has_arg, opt = long_has_args(opt, longopts)
if has_arg: if has_arg:
@ -98,19 +99,35 @@ def do_longs(opts, opt, longopts, args):
# Return: # Return:
# has_arg? # has_arg?
# full option name # full option name
# Assumes longopts has been sorted (ASCII order).
def long_has_args(opt, longopts): def long_has_args(opt, longopts):
optlen = len(opt)
for i in range(len(longopts)): for i in range(len(longopts)):
x, y = longopts[i][:optlen], longopts[i][optlen:] if longopts[i].startswith(opt):
if opt != x: break
continue else:
if y != '' and y != '=' and i+1 < len(longopts): raise GetoptError('option --%s not recognized' % opt, opt)
if opt == longopts[i+1][:optlen]: # opt is a prefix of longopts[i]; find j s.t. opt is a prefix of
raise GetoptError('option --%s not a unique prefix' % opt, opt) # each possibility in longopts[i:j]
if longopts[i][-1:] in ('=', ): j = i+1
return 1, longopts[i][:-1] while j < len(longopts) and longopts[j].startswith(opt):
return 0, longopts[i] j += 1
raise GetoptError('option --%s not recognized' % opt, opt) possibilities = longopts[i:j]
# Is there an exact match?
if opt in possibilities:
return 0, opt
elif opt + '=' in possibilities:
return 1, opt
# No exact match, so better be unique.
if len(possibilities) > 1:
# XXX since possibilities contains all valid continuations, might be
# nice to work them into the error msg
raise GetoptError('option --%s not a unique prefix' % opt, opt)
assert len(possibilities) == 1
unique_match = possibilities[0]
has_arg = unique_match.endswith('=')
if has_arg:
unique_match = unique_match[:-1]
return has_arg, unique_match
def do_shorts(opts, optstring, shortopts, args): def do_shorts(opts, optstring, shortopts, args):
while optstring != '': while optstring != '':