summaryrefslogtreecommitdiff
path: root/Build
diff options
context:
space:
mode:
authorGravatar Joey Hess <joey@kitenet.net>2014-06-13 02:18:31 -0400
committerGravatar Joey Hess <joey@kitenet.net>2014-06-13 02:18:31 -0400
commit9c45b88e31d9d04fa0b65b2c9c539716ce05372e (patch)
treeff5430311f68fefab4b2a91b773b75bd25f96852 /Build
parent92ad1f697141fc781429440362b352f2c3c43542 (diff)
make EvilSplicer re-box file-embed's ByteStrings
The armel autobuilder started failing: Assistant/WebApp/Types.hs:128:14: primitive string literal must contain only characters <= '\xFF' This fixes that.
Diffstat (limited to 'Build')
-rw-r--r--Build/EvilSplicer.hs37
1 files changed, 37 insertions, 0 deletions
diff --git a/Build/EvilSplicer.hs b/Build/EvilSplicer.hs
index a8046b994..6b80929af 100644
--- a/Build/EvilSplicer.hs
+++ b/Build/EvilSplicer.hs
@@ -310,6 +310,7 @@ mangleCode = flip_colon
. yesod_url_render_hack
. text_builder_hack
. nested_instances
+ . boxed_fileembed
. collapse_multiline_strings
. remove_package_version
. emptylambda
@@ -553,6 +554,42 @@ mangleCode = flip_colon
- The ; is added by case_layout. -}
flip_colon = replace "; : _ " "; _ : "
+{- Embedded files use unsafe packing, which is problimatic
+ - for several reasons, including that GHC sometimes omits trailing
+ - newlines in the file content, which leads to the wrong byte
+ - count. Also, GHC sometimes outputs unicode characters, which
+ - are not legal in unboxed strings.
+ -
+ - Avoid problems by converting:
+ - GHC.IO.unsafePerformIO
+ - (Data.ByteString.Unsafe.unsafePackAddressLen
+ - lllll
+ - "blabblah"#)),
+ - to:
+ - Data.ByteString.Char8.pack "blabblah"),
+ -
+ - Note that the string is often multiline. This only works if
+ - collapse_multiline_strings has run first.
+ -}
+boxed_fileembed :: String -> String
+boxed_fileembed = parsecAndReplace $ do
+ i <- indent
+ void $ string "GHC.IO.unsafePerformIO"
+ void newline
+ void indent
+ void $ string "(Data.ByteString.Unsafe.unsafePackAddressLen"
+ void newline
+ void indent
+ void number
+ void newline
+ void indent
+ void $ char '"'
+ s <- restOfLine
+ let s' = take (length s - 5) s
+ if "\"#))," `isSuffixOf` s
+ then return (i ++ "Data.ByteString.Char8.pack \"" ++ s' ++ "\"),\n")
+ else fail "not an unboxed string"
+
{- This works around a problem in the expanded template haskell for Yesod
- type-safe url rendering.
-