Expand out array literals inside literals

This commit is contained in:
Adam Sampson 2007-05-01 23:04:00 +00:00
parent 287fb8b922
commit e8a38a6f02
5 changed files with 51 additions and 6 deletions

View File

@ -292,11 +292,7 @@ genArrayLiteralElems aes
where
genElem :: A.ArrayElem -> CGen ()
genElem (A.ArrayElemArray aes) = genArrayLiteralElems aes
genElem (A.ArrayElemExpr e)
= do t <- typeOfExpression e
case t of
A.Array _ _ -> missing $ "array literal containing non-literal array: " ++ show e
_ -> genExpression e
genElem (A.ArrayElemExpr e) = genExpression e
genByteLiteral :: String -> CGen ()
genByteLiteral s

View File

@ -42,6 +42,9 @@ cgtests_targets = $(patsubst %.occ,%,$(cgtests))
all-cgtests: $(cgtests_targets)
clean-cgtests:
rm -f cgtests/cgtest?? cgtests/*.tock.*
haddock:
@mkdir -p doc
haddock -o doc --html $(sources)

View File

@ -6,6 +6,7 @@ import Data.Generics
import Data.Maybe
import qualified AST as A
import Errors
import Metadata
import ParseState
import Types
@ -17,6 +18,7 @@ simplifyExprs = runPasses passes
passes =
[ ("Convert FUNCTIONs to PROCs", functionsToProcs)
, ("Convert AFTER to MINUS", removeAfter)
, ("Expand array literals", expandArrayLiterals)
, ("Pull up definitions", pullUp)
]
@ -74,6 +76,30 @@ removeAfter = doGeneric `extM` doExpression
return $ A.Dyadic m A.More (A.Dyadic m A.Minus a' b') zero
doExpression e = doGeneric e
-- | For array literals that include other arrays, burst them into their elements.
expandArrayLiterals :: Data t => t -> PassM t
expandArrayLiterals = doGeneric `extM` doArrayElem
where
doGeneric :: Data t => t -> PassM t
doGeneric = gmapM expandArrayLiterals
doArrayElem :: A.ArrayElem -> PassM A.ArrayElem
doArrayElem ae@(A.ArrayElemExpr e)
= do e' <- expandArrayLiterals e
t <- typeOfExpression e'
case t of
A.Array ds _ -> expand ds e
_ -> doGeneric ae
doArrayElem ae = doGeneric ae
expand :: [A.Dimension] -> A.Expression -> PassM A.ArrayElem
expand [] e = return $ A.ArrayElemExpr e
expand (A.UnknownDimension:_) _
= die "array literal containing non-literal array of unknown size"
expand (A.Dimension n:ds) e
= liftM A.ArrayElemArray $ sequence [expand ds (A.SubscriptedExpr m (A.Subscript m $ makeConstant m i) e) | i <- [0 .. (n - 1)]]
where m = findMeta e
-- | Find things that need to be moved up to their enclosing Structured, and do
-- so.
pullUp :: Data t => t -> PassM t

View File

@ -35,6 +35,9 @@ names in it replaced appropriately.
## Passes
There should be a mkGeneric which produces a version of doGeneric that prunes
out things we don't need to recurse into -- like Strings.
Come up with an approach to combining simple passes to avoid multiple tree
walks (for example, giving passes a "next thing to try" parameter).
@ -80,6 +83,8 @@ Slice checks should not be generated if the slice is known to be safe.
PLACE should work.
Array comparisons generate silly code (rather than failing).
## Long-term
If we have constant folding, we're three-quarters of the way towards having an

View File

@ -2,6 +2,21 @@ PROC P ()
VAL [2][2]INT is IS
[[1, 2],
[3, 4]]:
VAL [2]INT row IS [42, 24]:
VAL [2][2]INT js IS [row, row]:
VAL [2][2]INT jjs IS [is[0], js[0]]:
VAL [][]INT jjjs IS [is[0], js[0]]:
VAL [][][]INT ks IS [js, js, js]:
INT x:
x := is[1][1]
SEQ
x := is[1][1]
ASSERT (x = 4)
ASSERT (row[0] = 42)
ASSERT (js[1][1] = 24)
ASSERT (jjs[0][1] = 2)
ASSERT (jjs[1][1] = 24)
SEQ y = 0 FOR 2
SEQ x = 0 FOR 2
ASSERT (jjs[x][y] = jjjs[x][y])
ASSERT (ks[0][0][0] = 42)
: