Use getopts parser to find 'read' arrays (fixes )

This commit is contained in:
Vidar Holen 2020-10-18 22:57:16 -07:00
parent 3104cec770
commit 256457c47a
2 changed files with 10 additions and 15 deletions

View File

@ -851,7 +851,8 @@ prop_checkArrayWithoutIndex6 = verifyTree checkArrayWithoutIndex "echo $PIPESTAT
prop_checkArrayWithoutIndex7 = verifyTree checkArrayWithoutIndex "a=(a b); a+=c"
prop_checkArrayWithoutIndex8 = verifyTree checkArrayWithoutIndex "declare -a foo; foo=bar;"
prop_checkArrayWithoutIndex9 = verifyTree checkArrayWithoutIndex "read -r -a arr <<< 'foo bar'; echo \"$arr\""
prop_checkArrayWithoutIndex10= verifyTree checkArrayWithoutIndex "read -ra arr <<< 'foo bar'; echo \"$arr\""
prop_checkArrayWithoutIndex10 = verifyTree checkArrayWithoutIndex "read -ra arr <<< 'foo bar'; echo \"$arr\""
prop_checkArrayWithoutIndex11 = verifyNotTree checkArrayWithoutIndex "read -rpfoobar r; r=42"
checkArrayWithoutIndex params _ =
doVariableFlowAnalysis readF writeF defaultMap (variableFlow params)
where

View File

@ -578,10 +578,14 @@ getModifiedVariableCommand base@(T_SimpleCommand id cmdPrefix (T_NormalWord _ (T
"builtin" ->
getModifiedVariableCommand $ T_SimpleCommand id cmdPrefix rest
"read" ->
let params = map getLiteral rest
readArrayVars = getReadArrayVariables rest
in
catMaybes $ takeWhile isJust (reverse params) ++ readArrayVars
let fallback = catMaybes $ takeWhile isJust (reverse $ map getLiteral rest)
in fromMaybe fallback $ do
parsed <- getGnuOpts flagsForRead rest
case lookup "a" parsed of
Just (_, var) -> (:[]) <$> getLiteralArray var
Nothing -> return $ catMaybes $
map (getLiteral . snd . snd) $ filter (null . fst) parsed
"getopts" ->
case rest of
opts:var:_ -> maybeToList $ getLiteral var
@ -698,16 +702,6 @@ getModifiedVariableCommand base@(T_SimpleCommand id cmdPrefix (T_NormalWord _ (T
guard $ isVariableName name
return (name, arg)
-- get all the array variables used in read, e.g. read -a arr
getReadArrayVariables args =
map (getLiteralArray . snd)
(filter (isArrayFlag . fst) (zip args (tail args)))
isArrayFlag x = case getLiteralString x of
Just ('-':'-':_) -> False
Just ('-':str) -> 'a' `elem` str
_ -> False
-- get the FLAGS_ variable created by a shflags DEFINE_ call
getFlagVariable (n:v:_) = do
name <- getLiteralString n