Skip to content

Commit 2be3896

Browse files
ckoparkarulysses4ever
authored andcommitted
wip: GHC integration
1 parent c2ba86d commit 2be3896

File tree

15 files changed

+724
-63
lines changed

15 files changed

+724
-63
lines changed

gibbon-compiler/src/Gibbon/Common.hs

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -232,6 +232,7 @@ data Mode = ToParse -- ^ Parse and then stop
232232
| RunMPL -- ^ Compile to SML & compile with MPL & run
233233
| Bench Var -- ^ Benchmark a particular function applied to the packed data within an input file.
234234
| BenchInput FilePath -- ^ Hardcode the input file to the benchmark in the C code.
235+
| Library Var -- ^ Compile as a library, with its main entry point given.
235236
deriving (Show, Read, Eq, Ord)
236237

237238
-- | Compilation backend used

gibbon-compiler/src/Gibbon/Compiler.hs

Lines changed: 17 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -9,7 +9,7 @@
99

1010
module Gibbon.Compiler
1111
( -- * Compiler entrypoints
12-
compile, compileCmd
12+
compile, compileFromL0, compileCmd
1313
-- * Configuration options and parsing
1414
, Config (..), Mode(..), Input(..)
1515
, configParser, configWithArgs, defaultConfig
@@ -163,7 +163,8 @@ configParser = Config <$> inputParser
163163
flag' RunMPL (long "mpl-run" <> help "Emit SML, compile with MPL, and run") <|>
164164
(Bench . toVar <$> strOption (short 'b' <> long "bench-fun" <> metavar "FUN" <>
165165
help ("Generate code to benchmark a 1-argument FUN against a input packed file."++
166-
" If --bench-input is provided, then the benchmark is run as well.")))
166+
" If --bench-input is provided, then the benchmark is run as well."))) <|>
167+
(Library <$> toVar <$> strOption (long "lib" <> metavar "FUN" <> help ("Compile as a library with its entry point given.")))
167168

168169
-- use C as the default backend
169170
backendParser :: Parser Backend
@@ -210,7 +211,7 @@ data CompileState a = CompileState
210211
-- | Compiler entrypoint, given a full configuration and a list of
211212
-- files to process, do the thing.
212213
compile :: Config -> FilePath -> IO ()
213-
compile config@Config{mode,input,verbosity,backend,cfile} fp0 = do
214+
compile config@Config{input,verbosity} fp0 = do
214215
-- set the env var DEBUG, to verbosity, when > 1
215216
setDebugEnvVar verbosity
216217

@@ -219,6 +220,11 @@ compile config@Config{mode,input,verbosity,backend,cfile} fp0 = do
219220
let fp1 = dir </> fp0
220221
-- Parse the input file
221222
((l0, cnt0), fp) <- parseInput config input fp1
223+
compileFromL0 config cnt0 fp l0
224+
225+
226+
compileFromL0 :: Config -> Int -> FilePath -> L0.Prog0 -> IO ()
227+
compileFromL0 config@Config{mode,backend,cfile} cnt0 fp l0 = do
222228
let config' = config { srcFile = Just fp }
223229

224230
let initTypeChecked :: L0.Prog0
@@ -272,19 +278,8 @@ compile config@Config{mode,input,verbosity,backend,cfile} fp0 = do
272278
C -> codegenProg config' l4
273279

274280

275-
276-
LLVM -> error $ "Cannot execute through the LLVM backend. To build Gibbon with LLVM: "
277-
++ "stack build --flag gibbon:llvm_enabled"
278-
279-
-- The C code is long, so put this at a higher verbosity level.
280-
dbgPrint passChatterLvl $ " [compiler] Final C codegen: " ++show (length str) ++" characters."
281-
dbgPrintLn 4 $ sepline ++ "\n" ++ str
282-
283-
clearFile outfile
284-
writeFile outfile str
285-
286281
-- (Stage 3) Code written, now compile if warranted.
287-
when (mode == ToExe || mode == RunExe || isBench mode ) $ do
282+
when (mode == ToExe || mode == RunExe || isBench mode || isLibrary mode) $ do
288283
compileAndRunExe config fp >>= putStr
289284
return ()
290285

@@ -423,6 +418,7 @@ compileAndRunExe cfg@Config{backend,arrayInput,benchInput,mode,cfile,exefile} fp
423418
_ -> return ""
424419
where outfile = getOutfile backend fp cfile
425420
exe = getExeFile backend fp exefile
421+
doto = replaceExtension fp ".o"
426422
pointer = gopt Opt_Pointer (dynflags cfg)
427423
links = if pointer
428424
then " -lgc -lm "
@@ -432,13 +428,14 @@ compileAndRunExe cfg@Config{backend,arrayInput,benchInput,mode,cfile,exefile} fp
432428
lib_dir <- getRTSBuildDir
433429
let rts_o_path = lib_dir </> "gibbon_rts.o"
434430
let compile_prog_cmd = compilationCmd backend cfg
435-
++ " -o " ++ exe
431+
++ (if isLibrary mode then (" -c -o " ++ doto) else (" -o " ++ exe))
436432
++" -I" ++ lib_dir
437433
++" -L" ++ lib_dir
438434
++ " -Wl,-rpath=" ++ lib_dir ++ " "
439435
++ outfile ++ " " ++ rts_o_path
440436
++ links ++ " -lgibbon_rts_ng"
441437

438+
putStrLn compile_prog_cmd
442439
execCmd
443440
Nothing
444441
compile_prog_cmd
@@ -541,6 +538,10 @@ isBench :: Mode -> Bool
541538
isBench (Bench _) = True
542539
isBench _ = False
543540

541+
isLibrary :: Mode -> Bool
542+
isLibrary (Library _) = True
543+
isLibrary _ = False
544+
544545
-- | The debug level at which we start to call the interpreter on the program during compilation.
545546
interpDbgLevel :: Int
546547
interpDbgLevel = 5

gibbon-compiler/src/Gibbon/Passes/Codegen.hs

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -202,7 +202,8 @@ codegenProg cfg prg@(Prog info_tbl sym_tbl funs mtal) =
202202
let struct_tys = uniqueDicts $ S.toList $ harvestStructTys prg
203203
return ((L.nub $ makeStructs struct_tys) ++ prots ++
204204
[gibTypesEnum, initInfoTable info_tbl, initSymTable sym_tbl] ++
205-
funs' ++ [main_expr'])
205+
funs' -- ++ [main_expr']
206+
)
206207

207208
main_expr :: PassM C.Definition
208209
main_expr = do

gibbon-compiler/src/Gibbon/Passes/Simplifier.hs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -93,8 +93,8 @@ simplifyL1 p0 = do
9393
p0' <- freshNames1 p0
9494
p1 <- markRecFns p0'
9595
p2 <- inlineFuns p1
96-
p3 <- deadFunElim p2
97-
pure p3
96+
-- p3 <- deadFunElim p2
97+
pure p2
9898

9999
--------------------------------------------------------------------------------
100100

gibbon-compiler/src/Gibbon/Pretty.hs

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,7 @@
55
{-# LANGUAGE ConstraintKinds #-}
66

77
module Gibbon.Pretty
8-
( Pretty(..), PPStyle(..), HasPretty, render, pprintHsWithEnv, pprender ) where
8+
( Pretty(..), PPStyle(..), HasPretty, render, pprintHsWithEnv, pprender, pprenderWithStyle ) where
99

1010
import Prelude hiding ((<>))
1111
import Text.PrettyPrint
@@ -41,6 +41,9 @@ class Pretty e where
4141
pprender :: Pretty e => e -> String
4242
pprender = render . pprint
4343

44+
pprenderWithStyle :: Pretty e => PPStyle -> e -> String
45+
pprenderWithStyle sty e = render $ pprintWithStyle sty e
46+
4447
doublecolon :: Doc
4548
doublecolon = colon <> colon
4649

gibbon-ghc-integration/cabal.project

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,7 @@
11
packages: ../gibbon-compiler
22
plugin0
33
plugin1
4+
gibbon-plugin
45
examples
56

67
with-compiler: ghc-9.4.3

gibbon-ghc-integration/examples/app/Main.hs

Lines changed: 22 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,11 @@
1+
{-# LANGUAGE BangPatterns #-}
2+
13
module Main ( main ) where
24

35
import BinTree -- ( fast_print_double, fast_print_double2 )
6+
import Measure
47

8+
import Control.Exception
59
import Data.Binary
610
import Data.ByteString.Lazy ( unpack )
711
import Data.Word
@@ -33,10 +37,27 @@ instance Binary Exp where
3337

3438
main :: IO ()
3539
main = do
40+
{-
3641
let expr = OpE (IntE 10) (IntE 11)
3742
print (unpack (encode expr))
38-
let tr = Node 10 (Leaf 10 10) (Leaf 20 20) :: Tree Int
43+
let tr = Node 10 (Leaf 10) (Leaf 20)
3944
print (unpack (encode tr))
45+
-}
46+
{-
4047
_ <- fast_print_double 3.0
4148
_ <- fast_print_double2 10.0
49+
-}
50+
51+
-- !n <- evaluate $ bench1 10
52+
-- print n
53+
-- !fastn <- fastbench1 10
54+
-- print fastn
55+
56+
let size = 22
57+
let iters = 9
58+
(res0, t0, t_all) <- bench bench1 size iters
59+
return (show res0, show t0, show t_all)
60+
61+
(res0, t0, t_all) <- bench fastbench1 size iters
62+
return (show res0, show t0, show t_all)
4263
pure ()
Lines changed: 108 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,108 @@
1+
{-# LANGUAGE BangPatterns #-}
2+
3+
module Measure where
4+
5+
import Control.Exception (evaluate)
6+
-- import Control.Monad.Par hiding (runParIO)
7+
-- import Control.Monad.Par.IO
8+
import Control.DeepSeq
9+
import Data.Int
10+
import Data.List
11+
import System.Mem (performMajorGC)
12+
import Data.Time.Clock (getCurrentTime, diffUTCTime)
13+
14+
--------------------------------------------------------------------------------
15+
16+
median :: [Double] -> Double
17+
median ls = (sort ls) !! (length ls `div` 2)
18+
19+
--------------------------------------------------------------------------------
20+
21+
22+
-- benchPar :: (NFData a, NFData b) =>
23+
-- (a -> Int64 -> Par b) -> a -> Int64 -> Int64 -> IO (b, Double, Double)
24+
-- benchPar f arg iters cutoff = do
25+
-- let !arg2 = force arg
26+
-- tups <- mapM (\_ -> dotrialPar f arg2 cutoff) [1..iters]
27+
-- let (results, times) = unzip tups
28+
-- -- print times
29+
-- let selftimed = median times
30+
-- batchtime = sum times
31+
-- return $! (last results, selftimed, batchtime)
32+
33+
-- benchParIO :: (NFData a, NFData b) =>
34+
-- (a -> Int64 -> ParIO b) -> a -> Int64 -> Int64 -> IO (b, Double, Double)
35+
-- benchParIO f arg iters cutoff = do
36+
-- let !arg2 = force arg
37+
-- tups <- mapM (\_ -> dotrialParIO f arg2 cutoff) [1..iters]
38+
-- let (results, times) = unzip tups
39+
-- -- print times
40+
-- let selftimed = median times
41+
-- batchtime = sum times
42+
-- return $! (last results, selftimed, batchtime)
43+
44+
benchIO :: (NFData a, NFData b) =>
45+
(a -> IO b) -> a -> Int64 -> IO (b, Double, Double)
46+
benchIO f arg iters = do
47+
let !arg2 = force arg
48+
tups <- mapM (\_ -> dotrialIO f arg2) [1..iters]
49+
let (results, times) = unzip tups
50+
-- print times
51+
let selftimed = median times
52+
batchtime = sum times
53+
return $! (last results, selftimed, batchtime)
54+
55+
56+
-- dotrialPar :: (NFData a, NFData b) =>
57+
-- (a -> Int64 -> Par b) -> a -> Int64 -> IO (b, Double)
58+
-- dotrialPar f arg cutoff = do
59+
-- performMajorGC
60+
-- t1 <- getCurrentTime
61+
-- !a <- evaluate$ runPar $ (f arg cutoff)
62+
-- t2 <- getCurrentTime
63+
-- let delt = fromRational (toRational (diffUTCTime t2 t1))
64+
-- putStrLn ("iter time: " ++ show delt)
65+
-- return $! (a,delt)
66+
67+
-- dotrialParIO :: (NFData a, NFData b) =>
68+
-- (a -> Int64 -> ParIO b) -> a -> Int64 -> IO (b, Double)
69+
-- dotrialParIO f arg cutoff = do
70+
-- performMajorGC
71+
-- t1 <- getCurrentTime
72+
-- !a <- runParIO $ (f arg cutoff)
73+
-- t2 <- getCurrentTime
74+
-- let delt = fromRational (toRational (diffUTCTime t2 t1))
75+
-- putStrLn ("iter time: " ++ show delt)
76+
-- return $! (a,delt)
77+
78+
dotrialIO :: (NFData a, NFData b) =>
79+
(a -> IO b) -> a -> IO (b, Double)
80+
dotrialIO f arg = do
81+
performMajorGC
82+
t1 <- getCurrentTime
83+
!a <- (f arg)
84+
t2 <- getCurrentTime
85+
let delt = fromRational (toRational (diffUTCTime t2 t1))
86+
putStrLn ("iter time: " ++ show delt)
87+
return $! (a,delt)
88+
89+
--------------------------------------------------------------------------------
90+
91+
bench :: (NFData a, Show b, NFData b) => (a -> b) -> a -> Int64 -> IO (b, Double, Double)
92+
bench f arg iters = do
93+
let !arg2 = force arg
94+
!tups <- mapM (\_ -> dotrial f arg2) [1..iters]
95+
let (results, times) = unzip tups
96+
let selftimed = median times
97+
batchtime = sum times
98+
return $! (last results, selftimed, batchtime)
99+
100+
dotrial :: (NFData a, Show b, NFData b) => (a -> b) -> a -> IO (b, Double)
101+
dotrial f arg = do
102+
performMajorGC
103+
t1 <- getCurrentTime
104+
!a <- evaluate $ (f arg)
105+
t2 <- getCurrentTime
106+
let delt = fromRational (toRational (diffUTCTime t2 t1))
107+
putStrLn ("iter time: " ++ show delt)
108+
return $! (a,delt)

gibbon-ghc-integration/examples/gibbon-examples.cabal

Lines changed: 28 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -8,34 +8,48 @@ library
88
hs-source-dirs: src
99
exposed-modules: BinTree
1010
build-depends: base == 4.17.*
11-
, plugin0
12-
, plugin1
11+
-- , plugin0
12+
-- , plugin1
1313
, inline-c
1414
, binary
15+
, gibbon-plugin
1516
ghc-options: -Wall -Wcompat -fdefer-typed-holes
1617
default-language: Haskell2010
1718
ghc-options: -Wall -Wcompat
18-
-fplugin=Gibbon.Plugin0
19-
-fplugin=Gibbon.Plugin1
19+
-O2
20+
-- -fplugin=Gibbon.Plugin0
21+
-- -fplugin=Gibbon.Plugin1
22+
-fplugin=Gibbon.Plugin
2023

21-
"-optl-Wl,--allow-multiple-definition"
24+
-- "-optl-Wl,--allow-multiple-definition"
2225
-- "-optl-Wl,--whole-archive"
23-
-- "-optl-Wl,-Bstatic"
24-
-- "-optl-Wl,-L/home/ckoparka/chai/tree-velocity/gibbon-ghc-integration/plugin1/cbits/"
25-
-- "-optl-Wl,-ltest2"
26-
-- "-optl-Wl,-Bdynamic"
26+
-- -- "-optl-Wl,-Bstatic"
27+
-- -- "-optl-Wl,-L/home/ckoparka/chai/tree-velocity/gibbon-ghc-integration/plugin1/cbits/"
28+
-- -- "-optl-Wl,-ltest2"
29+
-- "-optl-Wl,-I/home/ckoparka/chai/tree-velocity/gibbon-rts/build"
30+
-- "-optl-Wl,-L/home/ckoparka/chai/tree-velocity/gibbon-rts/build"
31+
-- "-optl-Wl,-lgibbon_rts_ng"
32+
-- -- "-optl-Wl,-Bdynamic"
33+
-- -- "-optl-Wl,-L/home/ckoparka/chai/tree-velocity/gibbon-rts/build"
2734
-- "-optl-Wl,--no-whole-archive"
2835

2936
-dcore-lint
3037
-ddump-simpl -dsuppress-all -ddump-to-file
3138

39+
include-dirs: "/home/ckoparka/chai/tree-velocity/gibbon-rts/build"
40+
extra-lib-dirs: "/home/ckoparka/chai/tree-velocity/gibbon-rts/build"
41+
extra-libraries: gibbon_rts_ng
42+
3243

3344
executable run-gibbon-examples
3445
hs-source-dirs: app
3546
default-language: Haskell2010
3647
main-is: Main.hs
37-
build-depends: base, gibbon-examples, binary, bytestring
38-
ghc-options:
39-
-- "-with-rtsopts=-T"
40-
-- "-with-rtsopts=-s"
41-
-dcore-lint
48+
build-depends: base, gibbon-examples, binary, bytestring, deepseq, time
49+
ghc-options: -O2
50+
-dcore-lint
51+
include-dirs: "/home/ckoparka/chai/tree-velocity/gibbon-rts/build"
52+
extra-lib-dirs: "/home/ckoparka/chai/tree-velocity/gibbon-rts/build"
53+
extra-libraries: gibbon_rts_ng
54+
-- ghc-options: "-optl-Wl,-I/home/ckoparka/chai/tree-velocity/gibbon-rts/build"
55+
-- "-optl-Wl,-L/home/ckoparka/chai/tree-velocity/gibbon-rts/build"

0 commit comments

Comments
 (0)