diff --git a/CHANGELOG b/CHANGELOG
--- a/CHANGELOG
+++ b/CHANGELOG
@@ -1,3 +1,8 @@
+2023-01-07
+        * Version bump (3.13). (#406)
+        * Declare local array variables in generated guards as pointers. (#401)
+        * Use pointer to pass output array as argument to generators. (#386)
+
 2022-11-07
         * Version bump (3.12). (#389)
         * Removed deprecated flag from cabal file. (#380)
diff --git a/copilot-c99.cabal b/copilot-c99.cabal
--- a/copilot-c99.cabal
+++ b/copilot-c99.cabal
@@ -1,6 +1,6 @@
 cabal-version             : >= 1.10
 name                      : copilot-c99
-version                   : 3.12
+version                   : 3.13
 synopsis                  : A compiler for Copilot targeting C99.
 description               :
   This package is a back-end from Copilot to C.
@@ -45,7 +45,7 @@
                           , mtl                 >= 2.2 && < 2.4
                           , pretty              >= 1.1 && < 1.2
 
-                          , copilot-core        >= 3.12  && < 3.13
+                          , copilot-core        >= 3.13  && < 3.14
                           , language-c99        >= 0.2.0 && < 0.3
                           , language-c99-simple >= 0.2.2 && < 0.3
 
diff --git a/src/Copilot/Compile/C99/CodeGen.hs b/src/Copilot/Compile/C99/CodeGen.hs
--- a/src/Copilot/Compile/C99/CodeGen.hs
+++ b/src/Copilot/Compile/C99/CodeGen.hs
@@ -12,6 +12,7 @@
 import qualified Language.C99.Simple as C
 
 import Copilot.Core
+import Copilot.Compile.C99.Error     (impossible)
 import Copilot.Compile.C99.Util
 import Copilot.Compile.C99.External
 import Copilot.Compile.C99.Settings
@@ -30,6 +31,28 @@
     cty = C.decay $ transtype ty
     (cexpr, cvars) = runState (transexpr expr) mempty
 
+-- | Write a generator function for a stream that returns an array.
+genFunArray :: String -> String -> Expr a -> Type a -> C.FunDef
+genFunArray name nameArg expr ty@(Array _) =
+    C.FunDef funType name [ outputParam ] varDecls stmts
+  where
+    funType = C.TypeSpec C.Void
+
+    -- The output value is an array
+    outputParam = C.Param cArrayType nameArg
+    cArrayType  = transtype ty
+
+    -- Output value, and any variable declarations needed
+    (cexpr, varDecls) = runState (transexpr expr) mempty
+
+    -- Copy expression to output argument
+    stmts = [ C.Expr $ memcpy (C.Ident nameArg) cexpr size ]
+    size  = C.LitInt (fromIntegral $ tysize ty)
+              C..* C.SizeOfType (C.TypeName $ tyElemName ty)
+
+genFunArray name nameArg expr _ =
+  impossible "genFunArray" "copilot-c99"
+
 -- | Make a extern declaration of a variable.
 mkextdecln :: External -> C.Decln
 mkextdecln (External name _ ty) = decln
@@ -99,10 +122,8 @@
           tmpdecln = C.VarDecln Nothing cty tmp_var Nothing
 
           tmpassign = case ty of
-            Array _ -> C.Expr $ memcpy (C.Ident tmp_var) val size
-              where
-                size = C.LitInt (fromIntegral $ tysize ty)
-                        C..* C.SizeOfType (C.TypeName (tyElemName ty))
+            Array _ -> C.Expr $ C.Funcall (C.Ident $ generatorname sid)
+                                          [ C.Ident tmp_var ]
             _       -> C.Expr $ C.Ident tmp_var C..= val
 
           bufferupdate = case ty of
@@ -219,20 +240,7 @@
             args'        = take (length args) (map argcall (argnames name))
             argcall name = C.Funcall (C.Ident name) []
 
-    -- Write a call to the memcpy function.
-    memcpy :: C.Expr -> C.Expr -> C.Expr -> C.Expr
-    memcpy dest src size = C.Funcall (C.Ident "memcpy") [dest, src, size]
 
-    -- Translate a Copilot type to a C99 type, handling arrays especially.
-    --
-    -- If the given type is an array (including multi-dimensional arrays), the
-    -- type is that of the elements in the array. Otherwise, it is just the
-    -- equivalent representation of the given type in C.
-    tyElemName :: Type a -> C.Type
-    tyElemName ty = case ty of
-      Array ty' -> tyElemName ty'
-      _         -> transtype ty
-
 -- | Write a struct declaration based on its definition.
 mkstructdecln :: Struct a => Type a -> C.Decln
 mkstructdecln (Struct x) = C.TypeDecln struct
@@ -278,3 +286,19 @@
   where
     streamexpr  (Stream _ _ expr ty)   = UExpr ty expr
     triggerexpr (Trigger _ guard args) = UExpr Bool guard : args
+
+-- * Auxiliary functions
+
+-- Write a call to the memcpy function.
+memcpy :: C.Expr -> C.Expr -> C.Expr -> C.Expr
+memcpy dest src size = C.Funcall (C.Ident "memcpy") [dest, src, size]
+
+-- Translate a Copilot type to a C99 type, handling arrays especially.
+--
+-- If the given type is an array (including multi-dimensional arrays), the
+-- type is that of the elements in the array. Otherwise, it is just the
+-- equivalent representation of the given type in C.
+tyElemName :: Type a -> C.Type
+tyElemName ty = case ty of
+  Array ty' -> tyElemName ty'
+  _         -> transtype ty
diff --git a/src/Copilot/Compile/C99/Compile.hs b/src/Copilot/Compile/C99/Compile.hs
--- a/src/Copilot/Compile/C99/Compile.hs
+++ b/src/Copilot/Compile/C99/Compile.hs
@@ -1,3 +1,4 @@
+{-# LANGUAGE GADTs #-}
 -- | Compile Copilot specifications to C99 code.
 module Copilot.Compile.C99.Compile
   ( compile
@@ -103,6 +104,8 @@
         accessdecln (Stream sid buff _ ty) = mkaccessdecln sid ty buff
 
         streamgen :: Stream -> C.FunDef
+        streamgen (Stream sid _ expr ty@(Array _)) =
+          genFunArray (generatorname sid) (generatorOutputArgName sid) expr ty
         streamgen (Stream sid _ expr ty) = genfun (generatorname sid) expr ty
 
         triggergen :: Trigger -> [C.FunDef]
diff --git a/src/Copilot/Compile/C99/Translate.hs b/src/Copilot/Compile/C99/Translate.hs
--- a/src/Copilot/Compile/C99/Translate.hs
+++ b/src/Copilot/Compile/C99/Translate.hs
@@ -18,7 +18,7 @@
 
 transexpr (Local ty1 _ name e1 e2) = do
   e1' <- transexpr e1
-  let cty1 = transtype ty1
+  let cty1 = transLocalVarDeclType ty1
       init = Just $ C.InitExpr e1'
   statetell [C.VarDecln Nothing cty1 name init]
 
@@ -302,6 +302,16 @@
     where
       length = Just $ C.LitInt $ fromIntegral $ tylength ty
   Struct s  -> C.TypeSpec $ C.Struct (typename s)
+
+-- | Translate a Copilot type to a valid (local) variable declaration C99 type.
+--
+-- If the type denotes an array, translate it to a pointer to whatever the
+-- array holds. This special case is needed when the type is used for a local
+-- variable declaration. We treat global variables differently (we generate
+-- list initializers).
+transLocalVarDeclType :: Type a -> C.Type
+transLocalVarDeclType (Array ty') = C.Ptr $ transtype ty'
+transLocalVarDeclType ty          = transtype ty
 
 -- | Translate a Copilot type intro a C typename
 transtypename :: Type a -> C.TypeName
diff --git a/src/Copilot/Compile/C99/Util.hs b/src/Copilot/Compile/C99/Util.hs
--- a/src/Copilot/Compile/C99/Util.hs
+++ b/src/Copilot/Compile/C99/Util.hs
@@ -47,6 +47,10 @@
 generatorname :: Id -> String
 generatorname sid = streamname sid ++ "_gen"
 
+-- | Turn stream id into name of its output argument array.
+generatorOutputArgName :: Id -> String
+generatorOutputArgName sid = streamname sid ++ "_output"
+
 -- | Turn the name of a trigger into a guard generator.
 guardname :: String -> String
 guardname name = name ++ "_guard"
