Cheng Shao pushed to branch wip/fix-ci-clean at Glasgow Haskell Compiler / GHC
Commits:
-
d6cf8463
by Peng Fan at 2025-12-06T11:06:28-05:00
-
9d371d23
by Matthew Pickering at 2025-12-06T11:07:09-05:00
-
0043bfb0
by Marc Scholten at 2025-12-06T11:08:03-05:00
-
fc958fc9
by Julian Ospald at 2025-12-06T11:08:53-05:00
-
0f297f6e
by mangoiv at 2025-12-06T11:09:44-05:00
-
72eab1d5
by Cheng Shao at 2025-12-06T19:44:01+01:00
30 changed files:
- .gitlab/ci.sh
- compiler/GHC/CmmToAsm/LA64/CodeGen.hs
- docs/users_guide/conf.py
- hadrian/src/Builder.hs
- hadrian/src/Rules/ToolArgs.hs
- hadrian/src/Settings/Builders/Ghc.hs
- hadrian/src/Settings/Default.hs
- libraries/xhtml
- rts/linker/LoadArchive.c
- utils/haddock/cabal.project
- utils/haddock/haddock-api/haddock-api.cabal
- utils/haddock/haddock-api/src/Haddock/Backends/Hoogle.hs
- utils/haddock/haddock-api/src/Haddock/Backends/Hyperlinker.hs
- utils/haddock/haddock-api/src/Haddock/Backends/Hyperlinker/Renderer.hs
- utils/haddock/haddock-api/src/Haddock/Backends/Xhtml.hs
- utils/haddock/haddock-api/src/Haddock/Backends/Xhtml/Decl.hs
- utils/haddock/haddock-api/src/Haddock/Backends/Xhtml/DocMarkup.hs
- utils/haddock/haddock-api/src/Haddock/Backends/Xhtml/Layout.hs
- utils/haddock/haddock-api/src/Haddock/Backends/Xhtml/Names.hs
- utils/haddock/haddock-api/src/Haddock/Backends/Xhtml/Themes.hs
- utils/haddock/haddock-api/src/Haddock/Backends/Xhtml/Utils.hs
- utils/haddock/haddock-api/src/Haddock/Doc.hs
- utils/haddock/haddock-api/src/Haddock/Utils.hs
- utils/haddock/html-test/ref/Bug26.html
- utils/haddock/html-test/ref/Bug298.html
- utils/haddock/html-test/ref/Bug458.html
- utils/haddock/html-test/ref/Nesting.html
- utils/haddock/html-test/ref/TitledPicture.html
- utils/haddock/html-test/ref/Unicode.html
- utils/haddock/html-test/ref/Unicode2.html
Changes:
| ... | ... | @@ -275,7 +275,7 @@ function setup() { |
| 275 | 275 | |
| 276 | 276 | function fetch_ghc() {
|
| 277 | 277 | local should_fetch=false
|
| 278 | -
|
|
| 278 | + |
|
| 279 | 279 | if [ ! -e "$GHC" ]; then
|
| 280 | 280 | if [ -z "${FETCH_GHC_VERSION:-}" ]; then
|
| 281 | 281 | fail "GHC not found at '$GHC' and FETCH_GHC_VERSION is not set"
|
| ... | ... | @@ -292,7 +292,7 @@ function fetch_ghc() { |
| 292 | 292 | fi
|
| 293 | 293 | fi
|
| 294 | 294 | fi
|
| 295 | -
|
|
| 295 | + |
|
| 296 | 296 | if [ "$should_fetch" = true ]; then
|
| 297 | 297 | local v="$FETCH_GHC_VERSION"
|
| 298 | 298 | |
| ... | ... | @@ -887,8 +887,24 @@ function save_cache () { |
| 887 | 887 | }
|
| 888 | 888 | |
| 889 | 889 | function clean() {
|
| 890 | - rm -R tmp
|
|
| 891 | - run rm -Rf _build
|
|
| 890 | + # When CI_DISPOSABLE_ENVIRONMENT is not true (e.g. using shell
|
|
| 891 | + # executor on windows/macos), the project directory is not removed
|
|
| 892 | + # by gitlab runner automatically after each job. To mitigate the
|
|
| 893 | + # space leak, other than periodic cleaning on the runner host, we
|
|
| 894 | + # also must aggressively cleanup build products, otherwise we run
|
|
| 895 | + # into out of space errors too frequently.
|
|
| 896 | + #
|
|
| 897 | + # When CI_DISPOSABLE_ENVIRONMENT is true (using docker executor on
|
|
| 898 | + # linux), the runner will do proper cleanup, so no need to do
|
|
| 899 | + # anything here.
|
|
| 900 | + if [[ "${CI_DISPOSABLE_ENVIRONMENT:-}" != true ]]; then
|
|
| 901 | + git submodule foreach --recursive git clean -xdf
|
|
| 902 | + git clean -xdf \
|
|
| 903 | + --exclude=ci_timings.txt \
|
|
| 904 | + --exclude=ghc-*.tar.xz \
|
|
| 905 | + --exclude=junit.xml \
|
|
| 906 | + --exclude=unexpected-test-output.tar.gz
|
|
| 907 | + fi
|
|
| 892 | 908 | }
|
| 893 | 909 | |
| 894 | 910 | function run_hadrian() {
|
| ... | ... | @@ -3,6 +3,7 @@ |
| 3 | 3 | {-# LANGUAGE BangPatterns #-}
|
| 4 | 4 | {-# LANGUAGE BinaryLiterals #-}
|
| 5 | 5 | {-# LANGUAGE OverloadedStrings #-}
|
| 6 | +{-# LANGUAGE MultiWayIf #-}
|
|
| 6 | 7 | module GHC.CmmToAsm.LA64.CodeGen (
|
| 7 | 8 | cmmTopCodeGen
|
| 8 | 9 | , generateJumpTableForInstr
|
| ... | ... | @@ -268,8 +269,10 @@ stmtToInstrs stmt = do |
| 268 | 269 | config <- getConfig
|
| 269 | 270 | platform <- getPlatform
|
| 270 | 271 | case stmt of
|
| 271 | - CmmUnsafeForeignCall target result_regs args
|
|
| 272 | - -> genCCall target result_regs args
|
|
| 272 | + CmmUnsafeForeignCall target result_regs args ->
|
|
| 273 | + case target of
|
|
| 274 | + PrimTarget primOp -> genPrim primOp result_regs args
|
|
| 275 | + ForeignTarget addr conv -> genCCall addr conv result_regs args
|
|
| 273 | 276 | |
| 274 | 277 | CmmComment s -> return (unitOL (COMMENT (ftext s)))
|
| 275 | 278 | CmmTick {} -> return nilOL
|
| ... | ... | @@ -1631,6 +1634,319 @@ genCondBranch true false expr = do |
| 1631 | 1634 | b2 <- genBranch false
|
| 1632 | 1635 | return (b1 `appOL` b2)
|
| 1633 | 1636 | |
| 1637 | +genPrim
|
|
| 1638 | + :: CallishMachOp -- MachOp
|
|
| 1639 | + -> [CmmFormal] -- where to put the result
|
|
| 1640 | + -> [CmmActual] -- arguments (of mixed type)
|
|
| 1641 | + -> NatM InstrBlock
|
|
| 1642 | + |
|
| 1643 | +genPrim MO_F32_Fabs [dst] [src] = genFloatAbs W32 dst src
|
|
| 1644 | +genPrim MO_F64_Fabs [dst] [src] = genFloatAbs W64 dst src
|
|
| 1645 | +genPrim MO_F32_Sqrt [dst] [src] = genFloatSqrt FF32 dst src
|
|
| 1646 | +genPrim MO_F64_Sqrt [dst] [src] = genFloatSqrt FF64 dst src
|
|
| 1647 | +genPrim (MO_Clz width) [dst] [src] = genClz width dst src
|
|
| 1648 | +genPrim (MO_Ctz width) [dst] [src] = genCtz width dst src
|
|
| 1649 | +genPrim (MO_BSwap width) [dst] [src] = genByteSwap width dst src
|
|
| 1650 | +genPrim (MO_BRev width) [dst] [src] = genBitRev width dst src
|
|
| 1651 | +genPrim MO_AcquireFence [] [] = return $ unitOL (DBAR HintAcquire)
|
|
| 1652 | +genPrim MO_ReleaseFence [] [] = return $ unitOL (DBAR HintRelease)
|
|
| 1653 | +genPrim MO_SeqCstFence [] [] = return $ unitOL (DBAR HintSeqcst)
|
|
| 1654 | +genPrim MO_Touch [] [_] = return nilOL
|
|
| 1655 | +genPrim (MO_Prefetch_Data _n) [] [_] = return nilOL
|
|
| 1656 | +genPrim (MO_AtomicRead w mo) [dst] [addr] = genAtomicRead w mo dst addr
|
|
| 1657 | +genPrim (MO_AtomicWrite w mo) [] [addr,val] = genAtomicWrite w mo addr val
|
|
| 1658 | + |
|
| 1659 | +genPrim mop@(MO_S_Mul2 _w) _ _ = unsupported mop
|
|
| 1660 | +genPrim mop@(MO_S_QuotRem _w) _ _ = unsupported mop
|
|
| 1661 | +genPrim mop@(MO_U_QuotRem _w) _ _ = unsupported mop
|
|
| 1662 | +genPrim mop@(MO_U_QuotRem2 _w) _ _ = unsupported mop
|
|
| 1663 | +genPrim mop@(MO_Add2 _w) _ _ = unsupported mop
|
|
| 1664 | +genPrim mop@(MO_AddWordC _w) _ _ = unsupported mop
|
|
| 1665 | +genPrim mop@(MO_SubWordC _w) _ _ = unsupported mop
|
|
| 1666 | +genPrim mop@(MO_AddIntC _w) _ _ = unsupported mop
|
|
| 1667 | +genPrim mop@(MO_SubIntC _w) _ _ = unsupported mop
|
|
| 1668 | +genPrim mop@(MO_U_Mul2 _w) _ _ = unsupported mop
|
|
| 1669 | +genPrim mop@MO_I64X2_Min _ _ = unsupported mop
|
|
| 1670 | +genPrim mop@MO_I64X2_Max _ _ = unsupported mop
|
|
| 1671 | +genPrim mop@MO_W64X2_Min _ _ = unsupported mop
|
|
| 1672 | +genPrim mop@MO_W64X2_Max _ _ = unsupported mop
|
|
| 1673 | +genPrim mop@MO_VS_Quot {} _ _ = unsupported mop
|
|
| 1674 | +genPrim mop@MO_VS_Rem {} _ _ = unsupported mop
|
|
| 1675 | +genPrim mop@MO_VU_Quot {} _ _ = unsupported mop
|
|
| 1676 | +genPrim mop@MO_VU_Rem {} _ _ = unsupported mop
|
|
| 1677 | + |
|
| 1678 | +genPrim (MO_PopCnt width) [dst] [src] = genLibCCall (popCntLabel width) [dst] [src]
|
|
| 1679 | +genPrim (MO_Pdep width) [dst] [src,mask] = genLibCCall (pdepLabel width) [dst] [src,mask]
|
|
| 1680 | +genPrim (MO_Pext width) [dst] [src,mask] = genLibCCall (pextLabel width) [dst] [src,mask]
|
|
| 1681 | +genPrim (MO_UF_Conv width) [dst] [src] = genLibCCall (word2FloatLabel width) [dst] [src]
|
|
| 1682 | +genPrim (MO_AtomicRMW width amop) [dst] [addr,n] = genLibCCall (atomicRMWLabel width amop) [dst] [addr,n]
|
|
| 1683 | +genPrim (MO_Cmpxchg width) [dst] [addr,old,new] = genLibCCall (cmpxchgLabel width) [dst] [addr,old,new]
|
|
| 1684 | +genPrim (MO_Xchg width) [dst] [addr,val] = genLibCCall (xchgLabel width) [dst] [addr,val]
|
|
| 1685 | +genPrim (MO_Memcpy _align) [] [dst,src,n] = genLibCCall (fsLit "memcpy") [] [dst,src,n]
|
|
| 1686 | +genPrim (MO_Memmove _align) [] [dst,src,n] = genLibCCall (fsLit "memmove") [] [dst,src,n]
|
|
| 1687 | +genPrim (MO_Memcmp _align) [rst] [dst,src,n] = genLibCCall (fsLit "memcmp") [rst] [dst,src,n]
|
|
| 1688 | +genPrim (MO_Memset _align) [] [dst,cnt,n] = genLibCCall (fsLit "memset") [] [dst,cnt,n]
|
|
| 1689 | +genPrim MO_F32_Sin [dst] [src] = genLibCCall (fsLit "sinf") [dst] [src]
|
|
| 1690 | +genPrim MO_F32_Cos [dst] [src] = genLibCCall (fsLit "cosf") [dst] [src]
|
|
| 1691 | +genPrim MO_F32_Tan [dst] [src] = genLibCCall (fsLit "tanf") [dst] [src]
|
|
| 1692 | +genPrim MO_F32_Exp [dst] [src] = genLibCCall (fsLit "expf") [dst] [src]
|
|
| 1693 | +genPrim MO_F32_ExpM1 [dst] [src] = genLibCCall (fsLit "expm1f") [dst] [src]
|
|
| 1694 | +genPrim MO_F32_Log [dst] [src] = genLibCCall (fsLit "logf") [dst] [src]
|
|
| 1695 | +genPrim MO_F32_Log1P [dst] [src] = genLibCCall (fsLit "log1pf") [dst] [src]
|
|
| 1696 | +genPrim MO_F32_Asin [dst] [src] = genLibCCall (fsLit "asinf") [dst] [src]
|
|
| 1697 | +genPrim MO_F32_Acos [dst] [src] = genLibCCall (fsLit "acosf") [dst] [src]
|
|
| 1698 | +genPrim MO_F32_Atan [dst] [src] = genLibCCall (fsLit "atanf") [dst] [src]
|
|
| 1699 | +genPrim MO_F32_Sinh [dst] [src] = genLibCCall (fsLit "sinhf") [dst] [src]
|
|
| 1700 | +genPrim MO_F32_Cosh [dst] [src] = genLibCCall (fsLit "coshf") [dst] [src]
|
|
| 1701 | +genPrim MO_F32_Tanh [dst] [src] = genLibCCall (fsLit "tanhf") [dst] [src]
|
|
| 1702 | +genPrim MO_F32_Pwr [dst] [x,y] = genLibCCall (fsLit "powf") [dst] [x,y]
|
|
| 1703 | +genPrim MO_F32_Asinh [dst] [src] = genLibCCall (fsLit "asinhf") [dst] [src]
|
|
| 1704 | +genPrim MO_F32_Acosh [dst] [src] = genLibCCall (fsLit "acoshf") [dst] [src]
|
|
| 1705 | +genPrim MO_F32_Atanh [dst] [src] = genLibCCall (fsLit "atanhf") [dst] [src]
|
|
| 1706 | +genPrim MO_F64_Sin [dst] [src] = genLibCCall (fsLit "sin") [dst] [src]
|
|
| 1707 | +genPrim MO_F64_Cos [dst] [src] = genLibCCall (fsLit "cos") [dst] [src]
|
|
| 1708 | +genPrim MO_F64_Tan [dst] [src] = genLibCCall (fsLit "tan") [dst] [src]
|
|
| 1709 | +genPrim MO_F64_Exp [dst] [src] = genLibCCall (fsLit "exp") [dst] [src]
|
|
| 1710 | +genPrim MO_F64_ExpM1 [dst] [src] = genLibCCall (fsLit "expm1") [dst] [src]
|
|
| 1711 | +genPrim MO_F64_Log [dst] [src] = genLibCCall (fsLit "log") [dst] [src]
|
|
| 1712 | +genPrim MO_F64_Log1P [dst] [src] = genLibCCall (fsLit "log1p") [dst] [src]
|
|
| 1713 | +genPrim MO_F64_Asin [dst] [src] = genLibCCall (fsLit "asin") [dst] [src]
|
|
| 1714 | +genPrim MO_F64_Acos [dst] [src] = genLibCCall (fsLit "acos") [dst] [src]
|
|
| 1715 | +genPrim MO_F64_Atan [dst] [src] = genLibCCall (fsLit "atan") [dst] [src]
|
|
| 1716 | +genPrim MO_F64_Sinh [dst] [src] = genLibCCall (fsLit "sinh") [dst] [src]
|
|
| 1717 | +genPrim MO_F64_Cosh [dst] [src] = genLibCCall (fsLit "cosh") [dst] [src]
|
|
| 1718 | +genPrim MO_F64_Tanh [dst] [src] = genLibCCall (fsLit "tanh") [dst] [src]
|
|
| 1719 | +genPrim MO_F64_Pwr [dst] [x,y] = genLibCCall (fsLit "pow") [dst] [x,y]
|
|
| 1720 | +genPrim MO_F64_Asinh [dst] [src] = genLibCCall (fsLit "asinh") [dst] [src]
|
|
| 1721 | +genPrim MO_F64_Acosh [dst] [src] = genLibCCall (fsLit "acosh") [dst] [src]
|
|
| 1722 | +genPrim MO_F64_Atanh [dst] [src] = genLibCCall (fsLit "atanh") [dst] [src]
|
|
| 1723 | +genPrim MO_SuspendThread [tok] [rs,i] = genLibCCall (fsLit "suspendThread") [tok] [rs,i]
|
|
| 1724 | +genPrim MO_ResumeThread [rs] [tok] = genLibCCall (fsLit "resumeThread") [rs] [tok]
|
|
| 1725 | +genPrim MO_I64_ToI [dst] [src] = genLibCCall (fsLit "hs_int64ToInt") [dst] [src]
|
|
| 1726 | +genPrim MO_I64_FromI [dst] [src] = genLibCCall (fsLit "hs_intToInt64") [dst] [src]
|
|
| 1727 | +genPrim MO_W64_ToW [dst] [src] = genLibCCall (fsLit "hs_word64ToWord") [dst] [src]
|
|
| 1728 | +genPrim MO_W64_FromW [dst] [src] = genLibCCall (fsLit "hs_wordToWord64") [dst] [src]
|
|
| 1729 | +genPrim MO_x64_Neg [dst] [src] = genLibCCall (fsLit "hs_neg64") [dst] [src]
|
|
| 1730 | +genPrim MO_x64_Add [dst] [src] = genLibCCall (fsLit "hs_add64") [dst] [src]
|
|
| 1731 | +genPrim MO_x64_Sub [dst] [src] = genLibCCall (fsLit "hs_sub64") [dst] [src]
|
|
| 1732 | +genPrim MO_x64_Mul [dst] [src] = genLibCCall (fsLit "hs_mul64") [dst] [src]
|
|
| 1733 | +genPrim MO_I64_Quot [dst] [src] = genLibCCall (fsLit "hs_quotInt64") [dst] [src]
|
|
| 1734 | +genPrim MO_I64_Rem [dst] [src] = genLibCCall (fsLit "hs_remInt64") [dst] [src]
|
|
| 1735 | +genPrim MO_W64_Quot [dst] [src] = genLibCCall (fsLit "hs_quotWord64") [dst] [src]
|
|
| 1736 | +genPrim MO_W64_Rem [dst] [src] = genLibCCall (fsLit "hs_remWord64") [dst] [src]
|
|
| 1737 | +genPrim MO_x64_And [dst] [src] = genLibCCall (fsLit "hs_and64") [dst] [src]
|
|
| 1738 | +genPrim MO_x64_Or [dst] [src] = genLibCCall (fsLit "hs_or64") [dst] [src]
|
|
| 1739 | +genPrim MO_x64_Xor [dst] [src] = genLibCCall (fsLit "hs_xor64") [dst] [src]
|
|
| 1740 | +genPrim MO_x64_Not [dst] [src] = genLibCCall (fsLit "hs_not64") [dst] [src]
|
|
| 1741 | +genPrim MO_x64_Shl [dst] [src] = genLibCCall (fsLit "hs_uncheckedShiftL64") [dst] [src]
|
|
| 1742 | +genPrim MO_I64_Shr [dst] [src] = genLibCCall (fsLit "hs_uncheckedIShiftRA64") [dst] [src]
|
|
| 1743 | +genPrim MO_W64_Shr [dst] [src] = genLibCCall (fsLit "hs_uncheckedShiftRL64") [dst] [src]
|
|
| 1744 | +genPrim MO_x64_Eq [dst] [src] = genLibCCall (fsLit "hs_eq64") [dst] [src]
|
|
| 1745 | +genPrim MO_x64_Ne [dst] [src] = genLibCCall (fsLit "hs_ne64") [dst] [src]
|
|
| 1746 | +genPrim MO_I64_Ge [dst] [src] = genLibCCall (fsLit "hs_geInt64") [dst] [src]
|
|
| 1747 | +genPrim MO_I64_Gt [dst] [src] = genLibCCall (fsLit "hs_gtInt64") [dst] [src]
|
|
| 1748 | +genPrim MO_I64_Le [dst] [src] = genLibCCall (fsLit "hs_leInt64") [dst] [src]
|
|
| 1749 | +genPrim MO_I64_Lt [dst] [src] = genLibCCall (fsLit "hs_ltInt64") [dst] [src]
|
|
| 1750 | +genPrim MO_W64_Ge [dst] [src] = genLibCCall (fsLit "hs_geWord64") [dst] [src]
|
|
| 1751 | +genPrim MO_W64_Gt [dst] [src] = genLibCCall (fsLit "hs_gtWord64") [dst] [src]
|
|
| 1752 | +genPrim MO_W64_Le [dst] [src] = genLibCCall (fsLit "hs_leWord64") [dst] [src]
|
|
| 1753 | +genPrim MO_W64_Lt [dst] [src] = genLibCCall (fsLit "hs_ltWord64") [dst] [src]
|
|
| 1754 | +genPrim op dst args = do
|
|
| 1755 | + platform <- ncgPlatform <$> getConfig
|
|
| 1756 | + pprPanic "genPrim: unknown primOp" (ppr (pprCallishMachOp op, dst, fmap (pdoc platform) args))
|
|
| 1757 | + |
|
| 1758 | + |
|
| 1759 | +genFloatAbs :: Width -> LocalReg -> CmmExpr -> NatM InstrBlock
|
|
| 1760 | +genFloatAbs w dst src = do
|
|
| 1761 | + platform <- getPlatform
|
|
| 1762 | + (reg_fx, _, code_fx) <- getFloatReg src
|
|
| 1763 | + let dst_reg = getRegisterReg platform (CmmLocal dst)
|
|
| 1764 | + return (code_fx `appOL` toOL
|
|
| 1765 | + [
|
|
| 1766 | + FABS (OpReg w dst_reg) (OpReg w reg_fx)
|
|
| 1767 | + ]
|
|
| 1768 | + )
|
|
| 1769 | + |
|
| 1770 | +genFloatSqrt :: Format -> LocalReg -> CmmExpr -> NatM InstrBlock
|
|
| 1771 | +genFloatSqrt f dst src = do
|
|
| 1772 | + platform <- getPlatform
|
|
| 1773 | + (reg_fx, _, code_fx) <- getFloatReg src
|
|
| 1774 | + let dst_reg = getRegisterReg platform (CmmLocal dst)
|
|
| 1775 | + return (code_fx `appOL` toOL
|
|
| 1776 | + [
|
|
| 1777 | + FSQRT (OpReg w dst_reg) (OpReg w reg_fx)
|
|
| 1778 | + ]
|
|
| 1779 | + )
|
|
| 1780 | + where
|
|
| 1781 | + w = case f of
|
|
| 1782 | + FF32 -> W32
|
|
| 1783 | + _ -> W64
|
|
| 1784 | + |
|
| 1785 | +genClz :: Width -> LocalReg -> CmmExpr -> NatM InstrBlock
|
|
| 1786 | +genClz w dst src = do
|
|
| 1787 | + platform <- getPlatform
|
|
| 1788 | + (reg_x, _, code_x) <- getSomeReg src
|
|
| 1789 | + let dst_reg = getRegisterReg platform (CmmLocal dst)
|
|
| 1790 | + if w `elem` [W32, W64] then do
|
|
| 1791 | + return (code_x `snocOL` CLZ (OpReg w dst_reg) (OpReg w reg_x))
|
|
| 1792 | + else if w `elem` [W8, W16] then do
|
|
| 1793 | + return (code_x `appOL` toOL
|
|
| 1794 | + [
|
|
| 1795 | + MOV (OpReg W64 dst_reg) (OpImm (ImmInt 1)),
|
|
| 1796 | + SLL (OpReg W64 dst_reg) (OpReg W64 dst_reg) (OpImm (ImmInt (31-shift))),
|
|
| 1797 | + SLL (OpReg W64 reg_x) (OpReg W64 reg_x) (OpImm (ImmInt (32-shift))),
|
|
| 1798 | + OR (OpReg W64 dst_reg) (OpReg W64 dst_reg) (OpReg W64 reg_x),
|
|
| 1799 | + CLZ (OpReg W64 dst_reg) (OpReg W32 dst_reg)
|
|
| 1800 | + ]
|
|
| 1801 | + )
|
|
| 1802 | + else do
|
|
| 1803 | + pprPanic "genClz: invalid width: " (ppr w)
|
|
| 1804 | + where
|
|
| 1805 | + shift = widthToInt w
|
|
| 1806 | + |
|
| 1807 | +genCtz :: Width -> LocalReg -> CmmExpr -> NatM InstrBlock
|
|
| 1808 | +genCtz w dst src = do
|
|
| 1809 | + platform <- getPlatform
|
|
| 1810 | + (reg_x, _, code_x) <- getSomeReg src
|
|
| 1811 | + let dst_reg = getRegisterReg platform (CmmLocal dst)
|
|
| 1812 | + if w `elem` [W32, W64] then do
|
|
| 1813 | + return (code_x `snocOL` CTZ (OpReg w dst_reg) (OpReg w reg_x))
|
|
| 1814 | + else if w `elem` [W8, W16] then do
|
|
| 1815 | + return (code_x `appOL` toOL
|
|
| 1816 | + [
|
|
| 1817 | + MOV (OpReg W64 dst_reg) (OpImm (ImmInt 1)),
|
|
| 1818 | + SLL (OpReg W64 dst_reg) (OpReg W64 dst_reg) (OpImm (ImmInt shift)),
|
|
| 1819 | + BSTRPICK II64 (OpReg W64 reg_x) (OpReg W64 reg_x) (OpImm (ImmInt (shift-1))) (OpImm (ImmInt 0)),
|
|
| 1820 | + OR (OpReg W64 dst_reg) (OpReg W64 dst_reg) (OpReg W64 reg_x),
|
|
| 1821 | + CTZ (OpReg W64 dst_reg) (OpReg W64 dst_reg)
|
|
| 1822 | + ]
|
|
| 1823 | + )
|
|
| 1824 | + else do
|
|
| 1825 | + pprPanic "genCtz: invalid width: " (ppr w)
|
|
| 1826 | + where
|
|
| 1827 | + shift = (widthToInt w)
|
|
| 1828 | + |
|
| 1829 | +genByteSwap :: Width -> LocalReg -> CmmExpr -> NatM InstrBlock
|
|
| 1830 | +genByteSwap w dst src = do
|
|
| 1831 | + platform <- getPlatform
|
|
| 1832 | + (reg_x, _, code_x) <- getSomeReg src
|
|
| 1833 | + let dst_reg = getRegisterReg platform (CmmLocal dst)
|
|
| 1834 | + case w of
|
|
| 1835 | + W64 ->
|
|
| 1836 | + return (code_x `appOL` toOL
|
|
| 1837 | + [
|
|
| 1838 | + REVBD (OpReg w dst_reg) (OpReg w reg_x)
|
|
| 1839 | + ]
|
|
| 1840 | + )
|
|
| 1841 | + W32 ->
|
|
| 1842 | + return (code_x `appOL` toOL
|
|
| 1843 | + [
|
|
| 1844 | + REVB2W (OpReg w dst_reg) (OpReg w reg_x)
|
|
| 1845 | + ]
|
|
| 1846 | + )
|
|
| 1847 | + W16 ->
|
|
| 1848 | + return (code_x `appOL` toOL
|
|
| 1849 | + [
|
|
| 1850 | + REVB2H (OpReg w dst_reg) (OpReg w reg_x)
|
|
| 1851 | + ]
|
|
| 1852 | + )
|
|
| 1853 | + _ -> pprPanic "genBSwap: invalid width: " (ppr w)
|
|
| 1854 | + |
|
| 1855 | +genBitRev :: Width -> LocalReg -> CmmExpr -> NatM InstrBlock
|
|
| 1856 | +genBitRev w dst src = do
|
|
| 1857 | + platform <- getPlatform
|
|
| 1858 | + (reg_x, _, code_x) <- getSomeReg src
|
|
| 1859 | + let dst_reg = getRegisterReg platform (CmmLocal dst)
|
|
| 1860 | + case w of
|
|
| 1861 | + W8 ->
|
|
| 1862 | + return (code_x `appOL` toOL
|
|
| 1863 | + [
|
|
| 1864 | + BITREV4B (OpReg W32 reg_x) (OpReg W32 reg_x),
|
|
| 1865 | + AND (OpReg W64 dst_reg) (OpReg W64 reg_x) (OpImm (ImmInt 255))
|
|
| 1866 | + ]
|
|
| 1867 | + )
|
|
| 1868 | + W16 ->
|
|
| 1869 | + return (code_x `appOL` toOL
|
|
| 1870 | + [
|
|
| 1871 | + BITREV (OpReg W64 reg_x) (OpReg W64 reg_x),
|
|
| 1872 | + SRL (OpReg W64 dst_reg) (OpReg W64 reg_x) (OpImm (ImmInt 48))
|
|
| 1873 | + ]
|
|
| 1874 | + )
|
|
| 1875 | + _ -> return ( code_x `snocOL` BITREV (OpReg w dst_reg) (OpReg w reg_x))
|
|
| 1876 | + |
|
| 1877 | +-- Generate C call to the given function in libc
|
|
| 1878 | +genLibCCall :: FastString -> [CmmFormal] -> [CmmActual] -> NatM InstrBlock
|
|
| 1879 | +genLibCCall name dsts args = do
|
|
| 1880 | + config <- getConfig
|
|
| 1881 | + target <-
|
|
| 1882 | + cmmMakeDynamicReference config CallReference
|
|
| 1883 | + $ mkForeignLabel name ForeignLabelInThisPackage IsFunction
|
|
| 1884 | + let cconv = ForeignConvention CCallConv [NoHint] [NoHint] CmmMayReturn
|
|
| 1885 | + genCCall target cconv dsts args
|
|
| 1886 | + |
|
| 1887 | +unsupported :: Show a => a -> b
|
|
| 1888 | +unsupported mop = panic ("outOfLineCmmOp: " ++ show mop
|
|
| 1889 | + ++ " not supported here")
|
|
| 1890 | + |
|
| 1891 | +-- AMSWAP_DB* insns implentment a fully functional synchronization barrier, like DBAR 0x0.
|
|
| 1892 | +-- This is terrible. And AMSWAPDB only supports ISA version greater than LA64V1_0. So,
|
|
| 1893 | +-- implement with DBAR
|
|
| 1894 | +genAtomicRead :: Width -> MemoryOrdering -> LocalReg -> CmmExpr -> NatM InstrBlock
|
|
| 1895 | +genAtomicRead w mo dst arg = do
|
|
| 1896 | + (addr_p, _, code_p) <- getSomeReg arg
|
|
| 1897 | + platform <- getPlatform
|
|
| 1898 | + let d = getRegisterReg platform (CmmLocal dst)
|
|
| 1899 | + case mo of
|
|
| 1900 | + MemOrderRelaxed ->
|
|
| 1901 | + return (code_p `appOL` toOL
|
|
| 1902 | + [
|
|
| 1903 | + LD (intFormat w) (OpReg w d) (OpAddr $ AddrReg addr_p)
|
|
| 1904 | + ]
|
|
| 1905 | + )
|
|
| 1906 | + |
|
| 1907 | + MemOrderAcquire ->
|
|
| 1908 | + return (code_p `appOL` toOL
|
|
| 1909 | + [
|
|
| 1910 | + LD (intFormat w) (OpReg w d) (OpAddr $ AddrReg addr_p),
|
|
| 1911 | + DBAR HintAcquire
|
|
| 1912 | + ]
|
|
| 1913 | + )
|
|
| 1914 | + MemOrderSeqCst ->
|
|
| 1915 | + return (code_p `appOL` toOL
|
|
| 1916 | + [
|
|
| 1917 | + LD (intFormat w) (OpReg w d) (OpAddr $ AddrReg addr_p),
|
|
| 1918 | + DBAR HintSeqcst
|
|
| 1919 | + ]
|
|
| 1920 | + )
|
|
| 1921 | + _ -> panic $ "Unexpected MemOrderRelease on an AtomicRead: " ++ show mo
|
|
| 1922 | + |
|
| 1923 | +genAtomicWrite :: Width -> MemoryOrdering -> CmmExpr -> CmmExpr -> NatM InstrBlock
|
|
| 1924 | +genAtomicWrite w mo addr val = do
|
|
| 1925 | + (addr_p, _, code_p) <- getSomeReg addr
|
|
| 1926 | + (val_reg, fmt_val, code_val) <- getSomeReg val
|
|
| 1927 | + case mo of
|
|
| 1928 | + MemOrderRelaxed ->
|
|
| 1929 | + return (code_p `appOL`code_val `appOL` toOL
|
|
| 1930 | + [
|
|
| 1931 | + ST fmt_val (OpReg w val_reg) (OpAddr $ AddrReg addr_p)
|
|
| 1932 | + ]
|
|
| 1933 | + )
|
|
| 1934 | + MemOrderRelease ->
|
|
| 1935 | + return (code_p `appOL`code_val `appOL` toOL
|
|
| 1936 | + [
|
|
| 1937 | + DBAR HintRelease,
|
|
| 1938 | + ST fmt_val (OpReg w val_reg) (OpAddr $ AddrReg addr_p)
|
|
| 1939 | + ]
|
|
| 1940 | + )
|
|
| 1941 | + MemOrderSeqCst ->
|
|
| 1942 | + return (code_p `appOL`code_val `appOL` toOL
|
|
| 1943 | + [
|
|
| 1944 | + DBAR HintSeqcst,
|
|
| 1945 | + ST fmt_val (OpReg w val_reg) (OpAddr $ AddrReg addr_p)
|
|
| 1946 | + ]
|
|
| 1947 | + )
|
|
| 1948 | + _ -> panic $ "Unexpected MemOrderAcquire on an AtomicWrite" ++ show mo
|
|
| 1949 | + |
|
| 1634 | 1950 | -- -----------------------------------------------------------------------------
|
| 1635 | 1951 | {-
|
| 1636 | 1952 | Generating C calls
|
| ... | ... | @@ -1664,393 +1980,68 @@ wider than FRLEN may be passed in a GAR. |
| 1664 | 1980 | -}
|
| 1665 | 1981 | |
| 1666 | 1982 | genCCall
|
| 1667 | - :: ForeignTarget -- function to call
|
|
| 1668 | - -> [CmmFormal] -- where to put the result
|
|
| 1669 | - -> [CmmActual] -- arguments (of mixed type)
|
|
| 1670 | - -> NatM InstrBlock
|
|
| 1671 | - |
|
| 1672 | --- TODO: Specialize where we can.
|
|
| 1673 | --- Generic impl
|
|
| 1674 | -genCCall target dest_regs arg_regs = do
|
|
| 1675 | - case target of
|
|
| 1676 | - -- The target :: ForeignTarget call can either
|
|
| 1677 | - -- be a foreign procedure with an address expr
|
|
| 1678 | - -- and a calling convention.
|
|
| 1679 | - ForeignTarget expr _cconv -> do
|
|
| 1680 | - (call_target, call_target_code) <- case expr of
|
|
| 1681 | - -- if this is a label, let's just directly to it.
|
|
| 1682 | - (CmmLit (CmmLabel lbl)) -> pure (TLabel lbl, nilOL)
|
|
| 1683 | - -- if it's not a label, let's compute the expression into a
|
|
| 1684 | - -- register and jump to that.
|
|
| 1685 | - _ -> do
|
|
| 1686 | - (reg, _format, reg_code) <- getSomeReg expr
|
|
| 1687 | - pure (TReg reg, reg_code)
|
|
| 1688 | - -- compute the code and register logic for all arg_regs.
|
|
| 1689 | - -- this will give us the format information to match on.
|
|
| 1690 | - arg_regs' <- mapM getSomeReg arg_regs
|
|
| 1691 | - |
|
| 1692 | - -- Now this is stupid. Our Cmm expressions doesn't carry the proper sizes
|
|
| 1693 | - -- so while in Cmm we might get W64 incorrectly for an int, that is W32 in
|
|
| 1694 | - -- STG; this thenn breaks packing of stack arguments, if we need to pack
|
|
| 1695 | - -- for the pcs, e.g. darwinpcs. Option one would be to fix the Int type
|
|
| 1696 | - -- in Cmm proper. Option two, which we choose here is to use extended Hint
|
|
| 1697 | - -- information to contain the size information and use that when packing
|
|
| 1698 | - -- arguments, spilled onto the stack.
|
|
| 1699 | - let (_res_hints, arg_hints) = foreignTargetHints target
|
|
| 1700 | - arg_regs'' = zipWith (\(r, f, c) h -> (r,f,h,c)) arg_regs' arg_hints
|
|
| 1701 | - |
|
| 1702 | - (stackSpaceWords, passRegs, passArgumentsCode) <- passArguments allGpArgRegs allFpArgRegs arg_regs'' 0 [] nilOL
|
|
| 1703 | - |
|
| 1704 | - readResultsCode <- readResults allGpArgRegs allFpArgRegs dest_regs [] nilOL
|
|
| 1705 | - |
|
| 1706 | - let moveStackDown 0 = toOL [ PUSH_STACK_FRAME
|
|
| 1707 | - , DELTA (-16)
|
|
| 1708 | - ]
|
|
| 1709 | - moveStackDown i | odd i = moveStackDown (i + 1)
|
|
| 1710 | - moveStackDown i = toOL [ PUSH_STACK_FRAME
|
|
| 1711 | - , SUB (OpReg W64 (spMachReg)) (OpReg W64 (spMachReg)) (OpImm (ImmInt (8 * i)))
|
|
| 1712 | - , DELTA (-8 * i - 16)
|
|
| 1713 | - ]
|
|
| 1714 | - moveStackUp 0 = toOL [ POP_STACK_FRAME
|
|
| 1715 | - , DELTA 0
|
|
| 1716 | - ]
|
|
| 1717 | - moveStackUp i | odd i = moveStackUp (i + 1)
|
|
| 1718 | - moveStackUp i = toOL [ ADD (OpReg W64 (spMachReg)) (OpReg W64 (spMachReg)) (OpImm (ImmInt (8 * i)))
|
|
| 1719 | - , POP_STACK_FRAME
|
|
| 1720 | - , DELTA 0
|
|
| 1721 | - ]
|
|
| 1722 | - |
|
| 1723 | - let code =
|
|
| 1724 | - call_target_code -- compute the label (possibly into a register)
|
|
| 1725 | - `appOL` moveStackDown (stackSpaceWords)
|
|
| 1726 | - `appOL` passArgumentsCode -- put the arguments into x0, ...
|
|
| 1727 | - `snocOL` CALL call_target passRegs -- branch and link (C calls aren't tail calls, but return)
|
|
| 1728 | - `appOL` readResultsCode -- parse the results into registers
|
|
| 1729 | - `appOL` moveStackUp (stackSpaceWords)
|
|
| 1730 | - return code
|
|
| 1731 | - |
|
| 1732 | - PrimTarget MO_F32_Fabs
|
|
| 1733 | - | [arg_reg] <- arg_regs, [dest_reg] <- dest_regs ->
|
|
| 1734 | - unaryFloatOp W32 (\d x -> unitOL $ FABS d x) arg_reg dest_reg
|
|
| 1735 | - | otherwise -> panic "mal-formed MO_F32_Fabs"
|
|
| 1736 | - PrimTarget MO_F64_Fabs
|
|
| 1737 | - | [arg_reg] <- arg_regs, [dest_reg] <- dest_regs ->
|
|
| 1738 | - unaryFloatOp W64 (\d x -> unitOL $ FABS d x) arg_reg dest_reg
|
|
| 1739 | - | otherwise -> panic "mal-formed MO_F64_Fabs"
|
|
| 1740 | - |
|
| 1741 | - PrimTarget MO_F32_Sqrt
|
|
| 1742 | - | [arg_reg] <- arg_regs, [dest_reg] <- dest_regs ->
|
|
| 1743 | - unaryFloatOp W32 (\d x -> unitOL $ FSQRT d x) arg_reg dest_reg
|
|
| 1744 | - | otherwise -> panic "mal-formed MO_F32_Sqrt"
|
|
| 1745 | - PrimTarget MO_F64_Sqrt
|
|
| 1746 | - | [arg_reg] <- arg_regs, [dest_reg] <- dest_regs ->
|
|
| 1747 | - unaryFloatOp W64 (\d x -> unitOL $ FSQRT d x) arg_reg dest_reg
|
|
| 1748 | - | otherwise -> panic "mal-formed MO_F64_Sqrt"
|
|
| 1749 | - |
|
| 1750 | - PrimTarget (MO_Clz w)
|
|
| 1751 | - | w `elem` [W32, W64],
|
|
| 1752 | - [arg_reg] <- arg_regs,
|
|
| 1753 | - [dest_reg] <- dest_regs -> do
|
|
| 1754 | - platform <- getPlatform
|
|
| 1755 | - (reg_x, _format_x, code_x) <- getSomeReg arg_reg
|
|
| 1756 | - let dst_reg = getRegisterReg platform (CmmLocal dest_reg)
|
|
| 1757 | - return ( code_x `snocOL`
|
|
| 1758 | - CLZ (OpReg w dst_reg) (OpReg w reg_x)
|
|
| 1759 | - )
|
|
| 1760 | - | w `elem` [W8, W16],
|
|
| 1761 | - [arg_reg] <- arg_regs,
|
|
| 1762 | - [dest_reg] <- dest_regs -> do
|
|
| 1763 | - platform <- getPlatform
|
|
| 1764 | - (reg_x, _format_x, code_x) <- getSomeReg arg_reg
|
|
| 1765 | - let dst_reg = getRegisterReg platform (CmmLocal dest_reg)
|
|
| 1766 | - return ( code_x `appOL` toOL
|
|
| 1767 | - [
|
|
| 1768 | - MOV (OpReg W64 dst_reg) (OpImm (ImmInt 1)),
|
|
| 1769 | - SLL (OpReg W64 dst_reg) (OpReg W64 dst_reg) (OpImm (ImmInt (31-shift))),
|
|
| 1770 | - SLL (OpReg W64 reg_x) (OpReg W64 reg_x) (OpImm (ImmInt (32-shift))),
|
|
| 1771 | - OR (OpReg W64 dst_reg) (OpReg W64 dst_reg) (OpReg W64 reg_x),
|
|
| 1772 | - CLZ (OpReg W64 dst_reg) (OpReg W32 dst_reg)
|
|
| 1773 | - ]
|
|
| 1774 | - )
|
|
| 1775 | - | otherwise -> unsupported (MO_Clz w)
|
|
| 1776 | - where
|
|
| 1777 | - shift = widthToInt w
|
|
| 1778 | - |
|
| 1779 | - PrimTarget (MO_Ctz w)
|
|
| 1780 | - | w `elem` [W32, W64],
|
|
| 1781 | - [arg_reg] <- arg_regs,
|
|
| 1782 | - [dest_reg] <- dest_regs -> do
|
|
| 1783 | - platform <- getPlatform
|
|
| 1784 | - (reg_x, _format_x, code_x) <- getSomeReg arg_reg
|
|
| 1785 | - let dst_reg = getRegisterReg platform (CmmLocal dest_reg)
|
|
| 1786 | - return ( code_x `snocOL`
|
|
| 1787 | - CTZ (OpReg w dst_reg) (OpReg w reg_x)
|
|
| 1788 | - )
|
|
| 1789 | - | w `elem` [W8, W16],
|
|
| 1790 | - [arg_reg] <- arg_regs,
|
|
| 1791 | - [dest_reg] <- dest_regs -> do
|
|
| 1792 | - platform <- getPlatform
|
|
| 1793 | - (reg_x, _format_x, code_x) <- getSomeReg arg_reg
|
|
| 1794 | - let dst_reg = getRegisterReg platform (CmmLocal dest_reg)
|
|
| 1795 | - return ( code_x `appOL` toOL
|
|
| 1796 | - [
|
|
| 1797 | - MOV (OpReg W64 dst_reg) (OpImm (ImmInt 1)),
|
|
| 1798 | - SLL (OpReg W64 dst_reg) (OpReg W64 dst_reg) (OpImm (ImmInt shift)),
|
|
| 1799 | - BSTRPICK II64 (OpReg W64 reg_x) (OpReg W64 reg_x) (OpImm (ImmInt (shift-1))) (OpImm (ImmInt 0)),
|
|
| 1800 | - OR (OpReg W64 dst_reg) (OpReg W64 dst_reg) (OpReg W64 reg_x),
|
|
| 1801 | - CTZ (OpReg W64 dst_reg) (OpReg W64 dst_reg)
|
|
| 1802 | - ]
|
|
| 1803 | - )
|
|
| 1804 | - | otherwise -> unsupported (MO_Ctz w)
|
|
| 1805 | - where
|
|
| 1806 | - shift = (widthToInt w)
|
|
| 1983 | + :: CmmExpr -- address of func call
|
|
| 1984 | + -> ForeignConvention -- calling convention
|
|
| 1985 | + -> [CmmFormal] -- results
|
|
| 1986 | + -> [CmmActual] -- arguments
|
|
| 1987 | + -> NatM InstrBlock
|
|
| 1988 | + |
|
| 1989 | + |
|
| 1990 | +genCCall expr _conv@(ForeignConvention _ argHints _resHints _) dest_regs arg_regs = do
|
|
| 1991 | + (call_target, call_target_code) <- case expr of
|
|
| 1992 | + -- if this is a label, let's just directly to it.
|
|
| 1993 | + (CmmLit (CmmLabel lbl)) -> pure (TLabel lbl, nilOL)
|
|
| 1994 | + -- if it's not a label, let's compute the expression into a
|
|
| 1995 | + -- register and jump to that.
|
|
| 1996 | + _ -> do
|
|
| 1997 | + (reg, _format, reg_code) <- getSomeReg expr
|
|
| 1998 | + pure (TReg reg, reg_code)
|
|
| 1999 | + -- compute the code and register logic for all arg_regs.
|
|
| 2000 | + -- this will give us the format information to match on.
|
|
| 2001 | + arg_regs' <- mapM getSomeReg arg_regs
|
|
| 2002 | + |
|
| 2003 | + -- Now this is stupid. Our Cmm expressions doesn't carry the proper sizes
|
|
| 2004 | + -- so while in Cmm we might get W64 incorrectly for an int, that is W32 in
|
|
| 2005 | + -- STG; this thenn breaks packing of stack arguments, if we need to pack
|
|
| 2006 | + -- for the pcs, e.g. darwinpcs. Option one would be to fix the Int type
|
|
| 2007 | + -- in Cmm proper. Option two, which we choose here is to use extended Hint
|
|
| 2008 | + -- information to contain the size information and use that when packing
|
|
| 2009 | + -- arguments, spilled onto the stack.
|
|
| 2010 | + let
|
|
| 2011 | + arg_hints = take (length arg_regs) (argHints ++ repeat NoHint)
|
|
| 2012 | + arg_regs'' = zipWith (\(r, f, c) h -> (r,f,h,c)) arg_regs' arg_hints
|
|
| 2013 | + |
|
| 2014 | + (stackSpaceWords, passRegs, passArgumentsCode) <- passArguments allGpArgRegs allFpArgRegs arg_regs'' 0 [] nilOL
|
|
| 2015 | + |
|
| 2016 | + readResultsCode <- readResults allGpArgRegs allFpArgRegs dest_regs [] nilOL
|
|
| 2017 | + |
|
| 2018 | + let moveStackDown 0 = toOL [ PUSH_STACK_FRAME
|
|
| 2019 | + , DELTA (-16)
|
|
| 2020 | + ]
|
|
| 2021 | + moveStackDown i | odd i = moveStackDown (i + 1)
|
|
| 2022 | + moveStackDown i = toOL [ PUSH_STACK_FRAME
|
|
| 2023 | + , SUB (OpReg W64 (spMachReg)) (OpReg W64 (spMachReg)) (OpImm (ImmInt (8 * i)))
|
|
| 2024 | + , DELTA (-8 * i - 16)
|
|
| 2025 | + ]
|
|
| 2026 | + moveStackUp 0 = toOL [ POP_STACK_FRAME
|
|
| 2027 | + , DELTA 0
|
|
| 2028 | + ]
|
|
| 2029 | + moveStackUp i | odd i = moveStackUp (i + 1)
|
|
| 2030 | + moveStackUp i = toOL [ ADD (OpReg W64 (spMachReg)) (OpReg W64 (spMachReg)) (OpImm (ImmInt (8 * i)))
|
|
| 2031 | + , POP_STACK_FRAME
|
|
| 2032 | + , DELTA 0
|
|
| 2033 | + ]
|
|
| 1807 | 2034 | |
| 1808 | - PrimTarget (MO_BSwap w)
|
|
| 1809 | - | w `elem` [W16, W32, W64],
|
|
| 1810 | - [arg_reg] <- arg_regs,
|
|
| 1811 | - [dest_reg] <- dest_regs -> do
|
|
| 1812 | - platform <- getPlatform
|
|
| 1813 | - (reg_x, _, code_x) <- getSomeReg arg_reg
|
|
| 1814 | - let dst_reg = getRegisterReg platform (CmmLocal dest_reg)
|
|
| 1815 | - case w of
|
|
| 1816 | - W64 -> return ( code_x `appOL` toOL
|
|
| 1817 | - [
|
|
| 1818 | - REVBD (OpReg w dst_reg) (OpReg w reg_x)
|
|
| 1819 | - ])
|
|
| 1820 | - W32 -> return ( code_x `appOL` toOL
|
|
| 1821 | - [
|
|
| 1822 | - REVB2W (OpReg w dst_reg) (OpReg w reg_x)
|
|
| 1823 | - ])
|
|
| 1824 | - _ -> return ( code_x `appOL` toOL
|
|
| 1825 | - [
|
|
| 1826 | - REVB2H (OpReg w dst_reg) (OpReg w reg_x)
|
|
| 1827 | - ])
|
|
| 1828 | - | otherwise -> unsupported (MO_BSwap w)
|
|
| 1829 | - |
|
| 1830 | - PrimTarget (MO_BRev w)
|
|
| 1831 | - | w `elem` [W8, W16, W32, W64],
|
|
| 1832 | - [arg_reg] <- arg_regs,
|
|
| 1833 | - [dest_reg] <- dest_regs -> do
|
|
| 1834 | - platform <- getPlatform
|
|
| 1835 | - (reg_x, _, code_x) <- getSomeReg arg_reg
|
|
| 1836 | - let dst_reg = getRegisterReg platform (CmmLocal dest_reg)
|
|
| 1837 | - case w of
|
|
| 1838 | - W8 -> return ( code_x `appOL` toOL
|
|
| 1839 | - [
|
|
| 1840 | - BITREV4B (OpReg W32 reg_x) (OpReg W32 reg_x),
|
|
| 1841 | - AND (OpReg W64 dst_reg) (OpReg W64 reg_x) (OpImm (ImmInt 255))
|
|
| 1842 | - ])
|
|
| 1843 | - W16 -> return ( code_x `appOL` toOL
|
|
| 1844 | - [
|
|
| 1845 | - BITREV (OpReg W64 reg_x) (OpReg W64 reg_x),
|
|
| 1846 | - SRL (OpReg W64 dst_reg) (OpReg W64 reg_x) (OpImm (ImmInt 48))
|
|
| 1847 | - ])
|
|
| 1848 | - _ -> return ( code_x `snocOL` BITREV (OpReg w dst_reg) (OpReg w reg_x))
|
|
| 1849 | - | otherwise -> unsupported (MO_BRev w)
|
|
| 1850 | - |
|
| 1851 | - -- mop :: CallishMachOp (see GHC.Cmm.MachOp)
|
|
| 1852 | - PrimTarget mop -> do
|
|
| 1853 | - -- We'll need config to construct forien targets
|
|
| 1854 | - case mop of
|
|
| 1855 | - -- 64 bit float ops
|
|
| 1856 | - MO_F64_Pwr -> mkCCall "pow"
|
|
| 1857 | - |
|
| 1858 | - MO_F64_Sin -> mkCCall "sin"
|
|
| 1859 | - MO_F64_Cos -> mkCCall "cos"
|
|
| 1860 | - MO_F64_Tan -> mkCCall "tan"
|
|
| 1861 | - |
|
| 1862 | - MO_F64_Sinh -> mkCCall "sinh"
|
|
| 1863 | - MO_F64_Cosh -> mkCCall "cosh"
|
|
| 1864 | - MO_F64_Tanh -> mkCCall "tanh"
|
|
| 1865 | - |
|
| 1866 | - MO_F64_Asin -> mkCCall "asin"
|
|
| 1867 | - MO_F64_Acos -> mkCCall "acos"
|
|
| 1868 | - MO_F64_Atan -> mkCCall "atan"
|
|
| 1869 | - |
|
| 1870 | - MO_F64_Asinh -> mkCCall "asinh"
|
|
| 1871 | - MO_F64_Acosh -> mkCCall "acosh"
|
|
| 1872 | - MO_F64_Atanh -> mkCCall "atanh"
|
|
| 1873 | - |
|
| 1874 | - MO_F64_Log -> mkCCall "log"
|
|
| 1875 | - MO_F64_Log1P -> mkCCall "log1p"
|
|
| 1876 | - MO_F64_Exp -> mkCCall "exp"
|
|
| 1877 | - MO_F64_ExpM1 -> mkCCall "expm1"
|
|
| 1878 | - |
|
| 1879 | - -- 32 bit float ops
|
|
| 1880 | - MO_F32_Pwr -> mkCCall "powf"
|
|
| 1881 | - |
|
| 1882 | - MO_F32_Sin -> mkCCall "sinf"
|
|
| 1883 | - MO_F32_Cos -> mkCCall "cosf"
|
|
| 1884 | - MO_F32_Tan -> mkCCall "tanf"
|
|
| 1885 | - MO_F32_Sinh -> mkCCall "sinhf"
|
|
| 1886 | - MO_F32_Cosh -> mkCCall "coshf"
|
|
| 1887 | - MO_F32_Tanh -> mkCCall "tanhf"
|
|
| 1888 | - MO_F32_Asin -> mkCCall "asinf"
|
|
| 1889 | - MO_F32_Acos -> mkCCall "acosf"
|
|
| 1890 | - MO_F32_Atan -> mkCCall "atanf"
|
|
| 1891 | - MO_F32_Asinh -> mkCCall "asinhf"
|
|
| 1892 | - MO_F32_Acosh -> mkCCall "acoshf"
|
|
| 1893 | - MO_F32_Atanh -> mkCCall "atanhf"
|
|
| 1894 | - MO_F32_Log -> mkCCall "logf"
|
|
| 1895 | - MO_F32_Log1P -> mkCCall "log1pf"
|
|
| 1896 | - MO_F32_Exp -> mkCCall "expf"
|
|
| 1897 | - MO_F32_ExpM1 -> mkCCall "expm1f"
|
|
| 1898 | - |
|
| 1899 | - -- 64-bit primops
|
|
| 1900 | - MO_I64_ToI -> mkCCall "hs_int64ToInt"
|
|
| 1901 | - MO_I64_FromI -> mkCCall "hs_intToInt64"
|
|
| 1902 | - MO_W64_ToW -> mkCCall "hs_word64ToWord"
|
|
| 1903 | - MO_W64_FromW -> mkCCall "hs_wordToWord64"
|
|
| 1904 | - MO_x64_Neg -> mkCCall "hs_neg64"
|
|
| 1905 | - MO_x64_Add -> mkCCall "hs_add64"
|
|
| 1906 | - MO_x64_Sub -> mkCCall "hs_sub64"
|
|
| 1907 | - MO_x64_Mul -> mkCCall "hs_mul64"
|
|
| 1908 | - MO_I64_Quot -> mkCCall "hs_quotInt64"
|
|
| 1909 | - MO_I64_Rem -> mkCCall "hs_remInt64"
|
|
| 1910 | - MO_W64_Quot -> mkCCall "hs_quotWord64"
|
|
| 1911 | - MO_W64_Rem -> mkCCall "hs_remWord64"
|
|
| 1912 | - MO_x64_And -> mkCCall "hs_and64"
|
|
| 1913 | - MO_x64_Or -> mkCCall "hs_or64"
|
|
| 1914 | - MO_x64_Xor -> mkCCall "hs_xor64"
|
|
| 1915 | - MO_x64_Not -> mkCCall "hs_not64"
|
|
| 1916 | - MO_x64_Shl -> mkCCall "hs_uncheckedShiftL64"
|
|
| 1917 | - MO_I64_Shr -> mkCCall "hs_uncheckedIShiftRA64"
|
|
| 1918 | - MO_W64_Shr -> mkCCall "hs_uncheckedShiftRL64"
|
|
| 1919 | - MO_x64_Eq -> mkCCall "hs_eq64"
|
|
| 1920 | - MO_x64_Ne -> mkCCall "hs_ne64"
|
|
| 1921 | - MO_I64_Ge -> mkCCall "hs_geInt64"
|
|
| 1922 | - MO_I64_Gt -> mkCCall "hs_gtInt64"
|
|
| 1923 | - MO_I64_Le -> mkCCall "hs_leInt64"
|
|
| 1924 | - MO_I64_Lt -> mkCCall "hs_ltInt64"
|
|
| 1925 | - MO_W64_Ge -> mkCCall "hs_geWord64"
|
|
| 1926 | - MO_W64_Gt -> mkCCall "hs_gtWord64"
|
|
| 1927 | - MO_W64_Le -> mkCCall "hs_leWord64"
|
|
| 1928 | - MO_W64_Lt -> mkCCall "hs_ltWord64"
|
|
| 1929 | - |
|
| 1930 | - -- Conversion
|
|
| 1931 | - MO_UF_Conv w -> mkCCall (word2FloatLabel w)
|
|
| 1932 | - |
|
| 1933 | - -- Optional MachOps
|
|
| 1934 | - -- These are enabled/disabled by backend flags: GHC.StgToCmm.Config
|
|
| 1935 | - MO_S_Mul2 _w -> unsupported mop
|
|
| 1936 | - MO_S_QuotRem _w -> unsupported mop
|
|
| 1937 | - MO_U_QuotRem _w -> unsupported mop
|
|
| 1938 | - MO_U_QuotRem2 _w -> unsupported mop
|
|
| 1939 | - MO_Add2 _w -> unsupported mop
|
|
| 1940 | - MO_AddWordC _w -> unsupported mop
|
|
| 1941 | - MO_SubWordC _w -> unsupported mop
|
|
| 1942 | - MO_AddIntC _w -> unsupported mop
|
|
| 1943 | - MO_SubIntC _w -> unsupported mop
|
|
| 1944 | - MO_U_Mul2 _w -> unsupported mop
|
|
| 1945 | - |
|
| 1946 | - MO_VS_Quot {} -> unsupported mop
|
|
| 1947 | - MO_VS_Rem {} -> unsupported mop
|
|
| 1948 | - MO_VU_Quot {} -> unsupported mop
|
|
| 1949 | - MO_VU_Rem {} -> unsupported mop
|
|
| 1950 | - MO_I64X2_Min -> unsupported mop
|
|
| 1951 | - MO_I64X2_Max -> unsupported mop
|
|
| 1952 | - MO_W64X2_Min -> unsupported mop
|
|
| 1953 | - MO_W64X2_Max -> unsupported mop
|
|
| 1954 | - |
|
| 1955 | - -- Memory Ordering
|
|
| 1956 | - -- Support finer-grained DBAR hints for LA664 and newer uarchs.
|
|
| 1957 | - -- These are treated as DBAR 0 on older uarchs, so we can start
|
|
| 1958 | - -- to unconditionally emit the new hints right away.
|
|
| 1959 | - MO_AcquireFence -> pure (unitOL (DBAR HintAcquire))
|
|
| 1960 | - MO_ReleaseFence -> pure (unitOL (DBAR HintRelease))
|
|
| 1961 | - MO_SeqCstFence -> pure (unitOL (DBAR HintSeqcst))
|
|
| 1962 | - |
|
| 1963 | - MO_Touch -> pure nilOL -- Keep variables live (when using interior pointers)
|
|
| 1964 | - -- Prefetch
|
|
| 1965 | - MO_Prefetch_Data _n -> pure nilOL -- Prefetch hint.
|
|
| 1966 | - |
|
| 1967 | - -- Memory copy/set/move/cmp, with alignment for optimization
|
|
| 1968 | - |
|
| 1969 | - -- TODO Optimize and use e.g. quad registers to move memory around instead
|
|
| 1970 | - -- of offloading this to memcpy. For small memcpys we can utilize
|
|
| 1971 | - -- the 128bit quad registers in NEON to move block of bytes around.
|
|
| 1972 | - -- Might also make sense of small memsets? Use xzr? What's the function
|
|
| 1973 | - -- call overhead?
|
|
| 1974 | - MO_Memcpy _align -> mkCCall "memcpy"
|
|
| 1975 | - MO_Memset _align -> mkCCall "memset"
|
|
| 1976 | - MO_Memmove _align -> mkCCall "memmove"
|
|
| 1977 | - MO_Memcmp _align -> mkCCall "memcmp"
|
|
| 1978 | - |
|
| 1979 | - MO_SuspendThread -> mkCCall "suspendThread"
|
|
| 1980 | - MO_ResumeThread -> mkCCall "resumeThread"
|
|
| 1981 | - |
|
| 1982 | - MO_PopCnt w -> mkCCall (popCntLabel w)
|
|
| 1983 | - MO_Pdep w -> mkCCall (pdepLabel w)
|
|
| 1984 | - MO_Pext w -> mkCCall (pextLabel w)
|
|
| 1985 | - |
|
| 1986 | - -- or a possibly side-effecting machine operation
|
|
| 1987 | - mo@(MO_AtomicRead w ord)
|
|
| 1988 | - | [p_reg] <- arg_regs
|
|
| 1989 | - , [dst_reg] <- dest_regs -> do
|
|
| 1990 | - (p, _fmt_p, code_p) <- getSomeReg p_reg
|
|
| 1991 | - platform <- getPlatform
|
|
| 1992 | - let instrs = case ord of
|
|
| 1993 | - MemOrderRelaxed -> unitOL $ ann moDescr (LD (intFormat w) (OpReg w dst) (OpAddr $ AddrReg p))
|
|
| 1994 | - |
|
| 1995 | - MemOrderAcquire -> toOL [
|
|
| 1996 | - ann moDescr (LD (intFormat w) (OpReg w dst) (OpAddr $ AddrReg p)),
|
|
| 1997 | - DBAR HintAcquire
|
|
| 1998 | - ]
|
|
| 1999 | - MemOrderSeqCst -> toOL [
|
|
| 2000 | - ann moDescr (LD (intFormat w) (OpReg w dst) (OpAddr $ AddrReg p)),
|
|
| 2001 | - DBAR HintSeqcst
|
|
| 2002 | - ]
|
|
| 2003 | - _ -> panic $ "Unexpected MemOrderRelease on an AtomicRead: " ++ show mo
|
|
| 2004 | - dst = getRegisterReg platform (CmmLocal dst_reg)
|
|
| 2005 | - moDescr = (text . show) mo
|
|
| 2006 | - code = code_p `appOL` instrs
|
|
| 2007 | - pure code
|
|
| 2008 | - | otherwise -> panic "mal-formed AtomicRead"
|
|
| 2009 | - |
|
| 2010 | - mo@(MO_AtomicWrite w ord)
|
|
| 2011 | - | [p_reg, val_reg] <- arg_regs -> do
|
|
| 2012 | - (p, _fmt_p, code_p) <- getSomeReg p_reg
|
|
| 2013 | - (val, fmt_val, code_val) <- getSomeReg val_reg
|
|
| 2014 | - let instrs = case ord of
|
|
| 2015 | - MemOrderRelaxed -> unitOL $ ann moDescr (ST fmt_val (OpReg w val) (OpAddr $ AddrReg p))
|
|
| 2016 | - -- AMSWAP_DB* insns implentment a fully functional synchronization barrier, like DBAR 0x0.
|
|
| 2017 | - -- This is terrible. And AMSWAPDB only supports ISA version greater than LA64V1_0. So,
|
|
| 2018 | - -- implement with DBAR
|
|
| 2019 | - MemOrderRelease -> toOL [
|
|
| 2020 | - ann moDescr (DBAR HintRelease),
|
|
| 2021 | - ST fmt_val (OpReg w val) (OpAddr $ AddrReg p)
|
|
| 2022 | - ]
|
|
| 2023 | - MemOrderSeqCst -> toOL [
|
|
| 2024 | - ann moDescr (DBAR HintSeqcst),
|
|
| 2025 | - ST fmt_val (OpReg w val) (OpAddr $ AddrReg p)
|
|
| 2026 | - ]
|
|
| 2027 | - _ -> panic $ "Unexpected MemOrderAcquire on an AtomicWrite" ++ show mo
|
|
| 2028 | - moDescr = (text . show) mo
|
|
| 2029 | - code =
|
|
| 2030 | - code_p `appOL`
|
|
| 2031 | - code_val `appOL`
|
|
| 2032 | - instrs
|
|
| 2033 | - pure code
|
|
| 2034 | - | otherwise -> panic "mal-formed AtomicWrite"
|
|
| 2035 | - |
|
| 2036 | - MO_AtomicRMW w amop -> mkCCall (atomicRMWLabel w amop)
|
|
| 2037 | - MO_Cmpxchg w -> mkCCall (cmpxchgLabel w)
|
|
| 2038 | - MO_Xchg w -> mkCCall (xchgLabel w)
|
|
| 2035 | + let code =
|
|
| 2036 | + call_target_code -- compute the label (possibly into a register)
|
|
| 2037 | + `appOL` moveStackDown (stackSpaceWords)
|
|
| 2038 | + `appOL` passArgumentsCode -- put the arguments into x0, ...
|
|
| 2039 | + `snocOL` CALL call_target passRegs -- branch and link (C calls aren't tail calls, but return)
|
|
| 2040 | + `appOL` readResultsCode -- parse the results into registers
|
|
| 2041 | + `appOL` moveStackUp (stackSpaceWords)
|
|
| 2042 | + return code
|
|
| 2039 | 2043 | |
| 2040 | 2044 | where
|
| 2041 | - unsupported :: Show a => a -> b
|
|
| 2042 | - unsupported mop = panic ("outOfLineCmmOp: " ++ show mop
|
|
| 2043 | - ++ " not supported here")
|
|
| 2044 | - |
|
| 2045 | - mkCCall :: FastString -> NatM InstrBlock
|
|
| 2046 | - mkCCall name = do
|
|
| 2047 | - config <- getConfig
|
|
| 2048 | - target <-
|
|
| 2049 | - cmmMakeDynamicReference config CallReference
|
|
| 2050 | - $ mkForeignLabel name ForeignLabelInThisPackage IsFunction
|
|
| 2051 | - let cconv = ForeignConvention CCallConv [NoHint] [NoHint] CmmMayReturn
|
|
| 2052 | - genCCall (ForeignTarget target cconv) dest_regs arg_regs
|
|
| 2053 | - |
|
| 2054 | 2045 | -- Implementiation of the LoongArch ABI calling convention.
|
| 2055 | 2046 | -- https://github.com/loongson/la-abi-specs/blob/release/lapcs.adoc#passing-arguments
|
| 2056 | 2047 | passArguments :: [Reg] -> [Reg] -> [(Reg, Format, ForeignHint, InstrBlock)] -> Int -> [Reg] -> InstrBlock -> NatM (Int, [Reg], InstrBlock)
|
| ... | ... | @@ -2129,10 +2120,10 @@ genCCall target dest_regs arg_regs = do |
| 2129 | 2120 | readResults _ _ [] _ accumCode = return accumCode
|
| 2130 | 2121 | readResults [] _ _ _ _ = do
|
| 2131 | 2122 | platform <- getPlatform
|
| 2132 | - pprPanic "genCCall, out of gp registers when reading results" (pdoc platform target)
|
|
| 2123 | + pprPanic "genCCall, out of gp registers when reading results" (pdoc platform expr)
|
|
| 2133 | 2124 | readResults _ [] _ _ _ = do
|
| 2134 | 2125 | platform <- getPlatform
|
| 2135 | - pprPanic "genCCall, out of fp registers when reading results" (pdoc platform target)
|
|
| 2126 | + pprPanic "genCCall, out of fp registers when reading results" (pdoc platform expr)
|
|
| 2136 | 2127 | readResults (gpReg:gpRegs) (fpReg:fpRegs) (dst:dsts) accumRegs accumCode = do
|
| 2137 | 2128 | -- gp/fp reg -> dst
|
| 2138 | 2129 | platform <- getPlatform
|
| ... | ... | @@ -2150,13 +2141,6 @@ genCCall target dest_regs arg_regs = do |
| 2150 | 2141 | -- truncate, otherwise an unexpectedly big value might be used in upfollowing calculations
|
| 2151 | 2142 | truncateReg W64 w r_dst
|
| 2152 | 2143 | |
| 2153 | - unaryFloatOp w op arg_reg dest_reg = do
|
|
| 2154 | - platform <- getPlatform
|
|
| 2155 | - (reg_fx, _format_x, code_fx) <- getFloatReg arg_reg
|
|
| 2156 | - let dst = getRegisterReg platform (CmmLocal dest_reg)
|
|
| 2157 | - let code = code_fx `appOL` op (OpReg w dst) (OpReg w reg_fx)
|
|
| 2158 | - pure code
|
|
| 2159 | - |
|
| 2160 | 2144 | data BlockInRange = InRange | NotInRange BlockId
|
| 2161 | 2145 | |
| 2162 | 2146 | genCondFarJump :: (MonadGetUnique m) => Cond -> Operand -> Operand -> BlockId -> m InstrBlock
|
| ... | ... | @@ -45,7 +45,7 @@ rst_prolog = """ |
| 45 | 45 | |
| 46 | 46 | # General information about the project.
|
| 47 | 47 | project = u'Glasgow Haskell Compiler'
|
| 48 | -copyright = f"{datetime.now(timezone.utc).year}, GHC Team"
|
|
| 48 | +copyright = "{}, GHC Team".format(datetime.now(timezone.utc).year)
|
|
| 49 | 49 | # N.B. version comes from ghc_config
|
| 50 | 50 | release = version # The full version, including alpha/beta/rc tags.
|
| 51 | 51 |
| ... | ... | @@ -361,6 +361,12 @@ instance H.Builder Builder where |
| 361 | 361 | |
| 362 | 362 | Haddock BuildPackage -> runHaddock path buildArgs buildInputs
|
| 363 | 363 | |
| 364 | + Ghc FindHsDependencies _ -> do
|
|
| 365 | + -- Use a response file for ghc -M invocations, to
|
|
| 366 | + -- avoid issues with command line size limit on
|
|
| 367 | + -- Windows (#26637)
|
|
| 368 | + runGhcWithResponse path buildArgs buildInputs
|
|
| 369 | + |
|
| 364 | 370 | HsCpp -> captureStdout
|
| 365 | 371 | |
| 366 | 372 | Make dir -> cmd' buildOptions path ["-C", dir] buildArgs
|
| ... | ... | @@ -403,6 +409,17 @@ runHaddock haddockPath flagArgs fileInputs = withTempFile $ \tmp -> do |
| 403 | 409 | writeFile' tmp $ escapeArgs fileInputs
|
| 404 | 410 | cmd [haddockPath] flagArgs ('@' : tmp)
|
| 405 | 411 | |
| 412 | +runGhcWithResponse :: FilePath -> [String] -> [FilePath] -> Action ()
|
|
| 413 | +runGhcWithResponse ghcPath flagArgs fileInputs = withTempFile $ \tmp -> do
|
|
| 414 | + |
|
| 415 | + writeFile' tmp $ escapeArgs fileInputs
|
|
| 416 | + |
|
| 417 | + -- We can't put the flags in a response file, because some flags
|
|
| 418 | + -- require empty arguments (such as the -dep-suffix flag), but
|
|
| 419 | + -- that isn't supported yet due to #26560.
|
|
| 420 | + cmd [ghcPath] flagArgs ('@' : tmp)
|
|
| 421 | + |
|
| 422 | + |
|
| 406 | 423 | -- TODO: Some builders are required only on certain platforms. For example,
|
| 407 | 424 | -- 'Objdump' is only required on OpenBSD and AIX. Add support for platform
|
| 408 | 425 | -- specific optional builders as soon as we can reliably test this feature.
|
| ... | ... | @@ -172,6 +172,7 @@ toolTargets = [ cabalSyntax |
| 172 | 172 | , time
|
| 173 | 173 | , semaphoreCompat
|
| 174 | 174 | , unlit -- # executable
|
| 175 | + , xhtml
|
|
| 175 | 176 | ] ++ if windowsHost then [ win32 ] else [ unix ]
|
| 176 | 177 | |
| 177 | 178 | -- | Create a mapping from files to which component it belongs to.
|
| ... | ... | @@ -182,7 +182,7 @@ findHsDependencies = builder (Ghc FindHsDependencies) ? do |
| 182 | 182 | , arg "-include-pkg-deps"
|
| 183 | 183 | , arg "-dep-makefile", arg =<< getOutput
|
| 184 | 184 | , pure $ concat [ ["-dep-suffix", wayPrefix w] | w <- Set.toList ways ]
|
| 185 | - , getInputs ]
|
|
| 185 | + ]
|
|
| 186 | 186 | |
| 187 | 187 | haddockGhcArgs :: Args
|
| 188 | 188 | haddockGhcArgs = mconcat [ commonGhcArgs
|
| ... | ... | @@ -109,6 +109,7 @@ stage0Packages = do |
| 109 | 109 | , thLift -- new library not yet present for boot compilers
|
| 110 | 110 | , thQuasiquoter -- new library not yet present for boot compilers
|
| 111 | 111 | , unlit
|
| 112 | + , xhtml -- new version is not backwards compat with latest
|
|
| 112 | 113 | , if windowsHost then win32 else unix
|
| 113 | 114 | -- We must use the in-tree `Win32` as the version
|
| 114 | 115 | -- bundled with GHC 9.6 is too old for `semaphore-compat`.
|
| 1 | -Subproject commit 68353ccd1a2e776d6c2b11619265d8140bb7dc07 |
|
| 1 | +Subproject commit cc203b9cc0a60c53a3bcbf2f38eb72cb7cf6098d |
| ... | ... | @@ -592,6 +592,9 @@ HsInt loadArchive_ (pathchar *path) |
| 592 | 592 | if (!readThinArchiveMember(n, memberSize, path, fileName, image)) {
|
| 593 | 593 | goto fail;
|
| 594 | 594 | }
|
| 595 | + // Unlike for regular archives for thin archives we can only identify the object format
|
|
| 596 | + // after having read the file pointed to.
|
|
| 597 | + object_fmt = identifyObjectFile_(image, memberSize);
|
|
| 595 | 598 | }
|
| 596 | 599 | else
|
| 597 | 600 | {
|
| ... | ... | @@ -12,4 +12,4 @@ package haddock-api |
| 12 | 12 | tests: False
|
| 13 | 13 | |
| 14 | 14 | -- Pinning the index-state helps to make reasonably CI deterministic
|
| 15 | -index-state: 2024-06-18T11:54:44Z |
|
| 15 | +index-state: 2025-11-17T03:30:46Z |
| ... | ... | @@ -51,6 +51,7 @@ common extensions |
| 51 | 51 | StrictData
|
| 52 | 52 | TypeApplications
|
| 53 | 53 | TypeOperators
|
| 54 | + OverloadedStrings
|
|
| 54 | 55 | |
| 55 | 56 | default-language: Haskell2010
|
| 56 | 57 | |
| ... | ... | @@ -81,7 +82,7 @@ library |
| 81 | 82 | build-depends: base >= 4.16 && < 4.23
|
| 82 | 83 | , ghc ^>= 9.15
|
| 83 | 84 | , haddock-library ^>= 1.11
|
| 84 | - , xhtml ^>= 3000.2.2
|
|
| 85 | + , xhtml ^>= 3000.4.0.0
|
|
| 85 | 86 | , parsec ^>= 3.1.13.0
|
| 86 | 87 | |
| 87 | 88 | -- Versions for the dependencies below are transitively pinned by
|
| ... | ... | @@ -97,6 +98,7 @@ library |
| 97 | 98 | , ghc-boot
|
| 98 | 99 | , mtl
|
| 99 | 100 | , transformers
|
| 101 | + , text
|
|
| 100 | 102 | |
| 101 | 103 | hs-source-dirs: src
|
| 102 | 104 | |
| ... | ... | @@ -212,7 +214,7 @@ test-suite spec |
| 212 | 214 | build-depends: ghc ^>= 9.7
|
| 213 | 215 | , ghc-paths ^>= 0.1.0.12
|
| 214 | 216 | , haddock-library ^>= 1.11
|
| 215 | - , xhtml ^>= 3000.2.2
|
|
| 217 | + , xhtml ^>= 3000.4.0.0
|
|
| 216 | 218 | , hspec ^>= 2.9
|
| 217 | 219 | , parsec ^>= 3.1.13.0
|
| 218 | 220 | , QuickCheck >= 2.11 && ^>= 2.14
|
| ... | ... | @@ -134,7 +134,7 @@ out :: Outputable a => SDocContext -> a -> String |
| 134 | 134 | out sDocContext = outWith $ Outputable.renderWithContext sDocContext
|
| 135 | 135 | |
| 136 | 136 | operator :: String -> String
|
| 137 | -operator (x : xs) | not (isAlphaNum x) && x `notElem` "_' ([{" = '(' : x : xs ++ ")"
|
|
| 137 | +operator (x : xs) | not (isAlphaNum x) && x `notElem` ("_' ([{" :: String) = '(' : x : xs ++ ")"
|
|
| 138 | 138 | operator x = x
|
| 139 | 139 | |
| 140 | 140 | commaSeparate :: Outputable a => SDocContext -> [a] -> String
|
| ... | ... | @@ -28,10 +28,11 @@ import Haddock.Backends.Hyperlinker.Parser |
| 28 | 28 | import Haddock.Backends.Hyperlinker.Renderer
|
| 29 | 29 | import Haddock.Backends.Hyperlinker.Types
|
| 30 | 30 | import Haddock.Backends.Hyperlinker.Utils
|
| 31 | -import Haddock.Backends.Xhtml.Utils (renderToString)
|
|
| 31 | +import Haddock.Backends.Xhtml.Utils (renderToBuilder)
|
|
| 32 | 32 | import Haddock.InterfaceFile
|
| 33 | 33 | import Haddock.Types
|
| 34 | -import Haddock.Utils (Verbosity, out, verbose, writeUtf8File)
|
|
| 34 | +import Haddock.Utils (Verbosity, out, verbose)
|
|
| 35 | +import qualified Data.ByteString.Builder as Builder
|
|
| 35 | 36 | |
| 36 | 37 | -- | Generate hyperlinked source for given interfaces.
|
| 37 | 38 | --
|
| ... | ... | @@ -117,7 +118,7 @@ ppHyperlinkedModuleSource verbosity srcdir pretty srcs iface = do |
| 117 | 118 | let tokens = fmap (\tk -> tk{tkSpan = (tkSpan tk){srcSpanFile = srcSpanFile $ nodeSpan fullAst}}) tokens'
|
| 118 | 119 | |
| 119 | 120 | -- Produce and write out the hyperlinked sources
|
| 120 | - writeUtf8File path . renderToString pretty . render' thisModule fullAst $ tokens
|
|
| 121 | + Builder.writeFile path . renderToBuilder pretty . render' thisModule fullAst $ tokens
|
|
| 121 | 122 | where
|
| 122 | 123 | dflags = ifaceDynFlags iface
|
| 123 | 124 | sDocContext = DynFlags.initSDocContext dflags Outputable.defaultUserStyle
|
| ... | ... | @@ -24,7 +24,9 @@ import qualified Text.XHtml as Html |
| 24 | 24 | import Haddock.Backends.Hyperlinker.Types
|
| 25 | 25 | import Haddock.Backends.Hyperlinker.Utils
|
| 26 | 26 | |
| 27 | -type StyleClass = String
|
|
| 27 | +import qualified Data.Text.Lazy as LText
|
|
| 28 | + |
|
| 29 | +type StyleClass = LText.Text
|
|
| 28 | 30 | |
| 29 | 31 | -- | Produce the HTML corresponding to a hyperlinked Haskell source
|
| 30 | 32 | render
|
| ... | ... | @@ -50,7 +52,7 @@ body thisModule srcs ast tokens = Html.body . Html.pre $ hypsrc |
| 50 | 52 | |
| 51 | 53 | header :: Maybe FilePath -> Maybe FilePath -> Html
|
| 52 | 54 | header Nothing Nothing = Html.noHtml
|
| 53 | -header mcss mjs = Html.header $ css mcss <> js mjs
|
|
| 55 | +header mcss mjs = Html.header $ css (LText.pack <$> mcss) <> js (LText.pack <$> mjs)
|
|
| 54 | 56 | where
|
| 55 | 57 | css Nothing = Html.noHtml
|
| 56 | 58 | css (Just cssFile) =
|
| ... | ... | @@ -225,7 +227,7 @@ tokenStyle TkPragma = ["hs-pragma"] |
| 225 | 227 | tokenStyle TkUnknown = []
|
| 226 | 228 | |
| 227 | 229 | multiclass :: [StyleClass] -> HtmlAttr
|
| 228 | -multiclass = Html.theclass . unwords
|
|
| 230 | +multiclass = Html.theclass . LText.unwords
|
|
| 229 | 231 | |
| 230 | 232 | externalAnchor :: Identifier -> Set.Set ContextInfo -> Html -> Html
|
| 231 | 233 | externalAnchor (Right name) contexts content
|
| ... | ... | @@ -250,11 +252,11 @@ internalAnchor (Right name) contexts content |
| 250 | 252 | Html.thespan content ! [Html.identifier $ internalAnchorIdent name]
|
| 251 | 253 | internalAnchor _ _ content = content
|
| 252 | 254 | |
| 253 | -externalAnchorIdent :: Name -> String
|
|
| 254 | -externalAnchorIdent = hypSrcNameUrl
|
|
| 255 | +externalAnchorIdent :: Name -> LText.Text
|
|
| 256 | +externalAnchorIdent name = LText.pack (hypSrcNameUrl name)
|
|
| 255 | 257 | |
| 256 | -internalAnchorIdent :: Name -> String
|
|
| 257 | -internalAnchorIdent = ("l-" ++) . showUnique . nameUnique
|
|
| 258 | +internalAnchorIdent :: Name -> LText.Text
|
|
| 259 | +internalAnchorIdent = LText.pack . ("l-" ++) . showUnique . nameUnique
|
|
| 258 | 260 | |
| 259 | 261 | -- | Generate the HTML hyperlink for an identifier
|
| 260 | 262 | hyperlink :: Module -> SrcMaps -> Identifier -> Html -> Html
|
| ... | ... | @@ -269,16 +271,16 @@ hyperlink thisModule (srcs, srcs') ident = case ident of |
| 269 | 271 | makeHyperlinkUrl url = ".." </> url
|
| 270 | 272 | |
| 271 | 273 | internalHyperlink name content =
|
| 272 | - Html.anchor content ! [Html.href $ "#" ++ internalAnchorIdent name]
|
|
| 274 | + Html.anchor content ! [Html.href $ "#" <> internalAnchorIdent name]
|
|
| 273 | 275 | |
| 274 | 276 | externalNameHyperlink name content = case Map.lookup mdl srcs of
|
| 275 | 277 | Just SrcLocal ->
|
| 276 | 278 | Html.anchor content
|
| 277 | - ! [Html.href $ hypSrcModuleNameUrl' thisModule mdl name]
|
|
| 279 | + ! [Html.href $ LText.pack (hypSrcModuleNameUrl' thisModule mdl name)]
|
|
| 278 | 280 | Just (SrcExternal path) ->
|
| 279 | 281 | let hyperlinkUrl = hypSrcModuleUrlToNameFormat $ makeHyperlinkUrl path
|
| 280 | 282 | in Html.anchor content
|
| 281 | - ! [Html.href $ spliceURL (Just mdl) (Just name) Nothing hyperlinkUrl]
|
|
| 283 | + ! [Html.href $ LText.pack $ spliceURL (Just mdl) (Just name) Nothing hyperlinkUrl]
|
|
| 282 | 284 | Nothing -> content
|
| 283 | 285 | where
|
| 284 | 286 | mdl = nameModule name
|
| ... | ... | @@ -287,11 +289,11 @@ hyperlink thisModule (srcs, srcs') ident = case ident of |
| 287 | 289 | case Map.lookup moduleName srcs' of
|
| 288 | 290 | Just SrcLocal ->
|
| 289 | 291 | Html.anchor content
|
| 290 | - ! [Html.href $ hypSrcModuleUrl' moduleName]
|
|
| 292 | + ! [Html.href $ LText.pack $ hypSrcModuleUrl' moduleName]
|
|
| 291 | 293 | Just (SrcExternal path) ->
|
| 292 | 294 | let hyperlinkUrl = makeHyperlinkUrl path
|
| 293 | 295 | in Html.anchor content
|
| 294 | - ! [Html.href $ spliceURL' (Just moduleName) Nothing Nothing hyperlinkUrl]
|
|
| 296 | + ! [Html.href $ LText.pack $ spliceURL' (Just moduleName) Nothing Nothing hyperlinkUrl]
|
|
| 295 | 297 | Nothing -> content
|
| 296 | 298 | |
| 297 | 299 | renderSpace :: Int -> String -> Html
|
| ... | ... | @@ -307,4 +309,4 @@ renderSpace line space = |
| 307 | 309 | in Html.toHtml hspace <> renderSpace line rest
|
| 308 | 310 | |
| 309 | 311 | lineAnchor :: Int -> Html
|
| 310 | -lineAnchor line = Html.thespan Html.noHtml ! [Html.identifier $ hypSrcLineUrl line] |
|
| 312 | +lineAnchor line = Html.thespan Html.noHtml ! [Html.identifier $ LText.pack $ hypSrcLineUrl line] |
| ... | ... | @@ -51,6 +51,10 @@ import qualified System.IO as IO |
| 51 | 51 | import Text.XHtml hiding (name, p, quote, title)
|
| 52 | 52 | import qualified Text.XHtml as XHtml
|
| 53 | 53 | import Prelude hiding (div)
|
| 54 | +import qualified Data.Text.Lazy as LText
|
|
| 55 | +import qualified Data.Text.Encoding as Text
|
|
| 56 | +import qualified Data.Text as Text
|
|
| 57 | +import qualified Data.ByteString.Lazy as LBS
|
|
| 54 | 58 | |
| 55 | 59 | import Haddock.Backends.Xhtml.Decl
|
| 56 | 60 | import Haddock.Backends.Xhtml.DocMarkup
|
| ... | ... | @@ -221,7 +225,7 @@ copyHtmlBits odir libdir themes withQuickjump = do |
| 221 | 225 | headHtml :: String -> Themes -> Maybe String -> Maybe String -> Html
|
| 222 | 226 | headHtml docTitle themes mathjax_url base_url =
|
| 223 | 227 | header
|
| 224 | - ! (maybe [] (\url -> [identifier "head", strAttr "data-base-url" url]) base_url)
|
|
| 228 | + ! (maybe [] (\url -> [identifier "head", strAttr "data-base-url" url]) (LText.pack <$> base_url))
|
|
| 225 | 229 | << [ meta ! [httpequiv "Content-Type", content "text/html; charset=UTF-8"]
|
| 226 | 230 | , meta ! [XHtml.name "viewport", content "width=device-width, initial-scale=1"]
|
| 227 | 231 | , thetitle << docTitle
|
| ... | ... | @@ -229,18 +233,18 @@ headHtml docTitle themes mathjax_url base_url = |
| 229 | 233 | , thelink
|
| 230 | 234 | ! [ rel "stylesheet"
|
| 231 | 235 | , thetype "text/css"
|
| 232 | - , href (withBaseURL base_url quickJumpCssFile)
|
|
| 236 | + , href (LText.pack $ withBaseURL base_url quickJumpCssFile)
|
|
| 233 | 237 | ]
|
| 234 | 238 | << noHtml
|
| 235 | 239 | , thelink ! [rel "stylesheet", thetype "text/css", href fontUrl] << noHtml
|
| 236 | 240 | , script
|
| 237 | - ! [ src (withBaseURL base_url haddockJsFile)
|
|
| 241 | + ! [ src (LText.pack $ withBaseURL base_url haddockJsFile)
|
|
| 238 | 242 | , emptyAttr "async"
|
| 239 | 243 | , thetype "text/javascript"
|
| 240 | 244 | ]
|
| 241 | 245 | << noHtml
|
| 242 | 246 | , script ! [thetype "text/x-mathjax-config"] << primHtml mjConf
|
| 243 | - , script ! [src mjUrl, thetype "text/javascript"] << noHtml
|
|
| 247 | + , script ! [src (LText.pack mjUrl), thetype "text/javascript"] << noHtml
|
|
| 244 | 248 | ]
|
| 245 | 249 | where
|
| 246 | 250 | fontUrl = "https://fonts.googleapis.com/css?family=PT+Sans:400,400i,700"
|
| ... | ... | @@ -257,31 +261,31 @@ headHtml docTitle themes mathjax_url base_url = |
| 257 | 261 | |
| 258 | 262 | srcButton :: SourceURLs -> Maybe Interface -> Maybe Html
|
| 259 | 263 | srcButton (Just src_base_url, _, _, _) Nothing =
|
| 260 | - Just (anchor ! [href src_base_url] << "Source")
|
|
| 264 | + Just (anchor ! [href (LText.pack src_base_url)] << ("Source" :: LText))
|
|
| 261 | 265 | srcButton (_, Just src_module_url, _, _) (Just iface) =
|
| 262 | 266 | let url = spliceURL (Just $ ifaceMod iface) Nothing Nothing src_module_url
|
| 263 | - in Just (anchor ! [href url] << "Source")
|
|
| 267 | + in Just (anchor ! [href (LText.pack url)] << ("Source" :: LText))
|
|
| 264 | 268 | srcButton _ _ =
|
| 265 | 269 | Nothing
|
| 266 | 270 | |
| 267 | 271 | wikiButton :: WikiURLs -> Maybe Module -> Maybe Html
|
| 268 | 272 | wikiButton (Just wiki_base_url, _, _) Nothing =
|
| 269 | - Just (anchor ! [href wiki_base_url] << "User Comments")
|
|
| 273 | + Just (anchor ! [href (LText.pack wiki_base_url)] << ("User Comments" :: LText))
|
|
| 270 | 274 | wikiButton (_, Just wiki_module_url, _) (Just mdl) =
|
| 271 | 275 | let url = spliceURL (Just mdl) Nothing Nothing wiki_module_url
|
| 272 | - in Just (anchor ! [href url] << "User Comments")
|
|
| 276 | + in Just (anchor ! [href (LText.pack url)] << ("User Comments" :: LText))
|
|
| 273 | 277 | wikiButton _ _ =
|
| 274 | 278 | Nothing
|
| 275 | 279 | |
| 276 | 280 | contentsButton :: Maybe String -> Maybe Html
|
| 277 | 281 | contentsButton maybe_contents_url =
|
| 278 | - Just (anchor ! [href url] << "Contents")
|
|
| 282 | + Just (anchor ! [href (LText.pack url)] << ("Contents" :: LText))
|
|
| 279 | 283 | where
|
| 280 | 284 | url = fromMaybe contentsHtmlFile maybe_contents_url
|
| 281 | 285 | |
| 282 | 286 | indexButton :: Maybe String -> Maybe Html
|
| 283 | 287 | indexButton maybe_index_url =
|
| 284 | - Just (anchor ! [href url] << "Index")
|
|
| 288 | + Just (anchor ! [href (LText.pack url)] << ("Index" :: LText))
|
|
| 285 | 289 | where
|
| 286 | 290 | url = fromMaybe indexHtmlFile maybe_index_url
|
| 287 | 291 | |
| ... | ... | @@ -318,8 +322,8 @@ bodyHtml |
| 318 | 322 | , divContent << pageContent
|
| 319 | 323 | , divFooter
|
| 320 | 324 | << paragraph
|
| 321 | - << ( "Produced by "
|
|
| 322 | - +++ (anchor ! [href projectUrl] << toHtml projectName)
|
|
| 325 | + << ( ("Produced by " :: LText)
|
|
| 326 | + +++ (anchor ! [href (LText.pack projectUrl)] << toHtml projectName)
|
|
| 323 | 327 | +++ (" version " ++ projectVersion)
|
| 324 | 328 | )
|
| 325 | 329 | ]
|
| ... | ... | @@ -368,7 +372,7 @@ moduleInfo iface = |
| 368 | 372 | xs -> extField $ unordList xs ! [theclass "extension-list"]
|
| 369 | 373 | | otherwise = []
|
| 370 | 374 | where
|
| 371 | - extField x = return $ th << "Extensions" <-> td << x
|
|
| 375 | + extField x = return $ th << ("Extensions" :: LText) <-> td << x
|
|
| 372 | 376 | dropOpt x = if "Opt_" `isPrefixOf` x then drop 4 x else x
|
| 373 | 377 | in
|
| 374 | 378 | case entries of
|
| ... | ... | @@ -454,7 +458,7 @@ ppHtmlContents |
| 454 | 458 | , ppModuleTrees pkg qual trees
|
| 455 | 459 | ]
|
| 456 | 460 | createDirectoryIfMissing True odir
|
| 457 | - writeUtf8File (joinPath [odir, contentsHtmlFile]) (renderToString debug html)
|
|
| 461 | + Builder.writeFile (joinPath [odir, contentsHtmlFile]) (renderToBuilder debug html)
|
|
| 458 | 462 | where
|
| 459 | 463 | -- Extract a module's short description.
|
| 460 | 464 | toInstalledDescription :: InstalledInterface -> Maybe (MDoc Name)
|
| ... | ... | @@ -472,11 +476,11 @@ ppPrologue pkg qual title (Just doc) = |
| 472 | 476 | ppSignatureTrees :: Maybe Package -> Qualification -> [(PackageInfo, [ModuleTree])] -> Html
|
| 473 | 477 | ppSignatureTrees _ _ tss | all (null . snd) tss = mempty
|
| 474 | 478 | ppSignatureTrees pkg qual [(info, ts)] =
|
| 475 | - divPackageList << (sectionName << "Signatures" +++ ppSignatureTree pkg qual "n" info ts)
|
|
| 479 | + divPackageList << (sectionName << ("Signatures" :: LText) +++ ppSignatureTree pkg qual "n" info ts)
|
|
| 476 | 480 | ppSignatureTrees pkg qual tss =
|
| 477 | 481 | divModuleList
|
| 478 | 482 | << ( sectionName
|
| 479 | - << "Signatures"
|
|
| 483 | + << ("Signatures" :: LText)
|
|
| 480 | 484 | +++ concatHtml
|
| 481 | 485 | [ ppSignatureTree pkg qual ("n." ++ show i ++ ".") info ts
|
| 482 | 486 | | (i, (info, ts)) <- zip [(1 :: Int) ..] tss
|
| ... | ... | @@ -491,11 +495,11 @@ ppSignatureTree pkg qual p info ts = |
| 491 | 495 | ppModuleTrees :: Maybe Package -> Qualification -> [(PackageInfo, [ModuleTree])] -> Html
|
| 492 | 496 | ppModuleTrees _ _ tss | all (null . snd) tss = mempty
|
| 493 | 497 | ppModuleTrees pkg qual [(info, ts)] =
|
| 494 | - divModuleList << (sectionName << "Modules" +++ ppModuleTree pkg qual "n" info ts)
|
|
| 498 | + divModuleList << (sectionName << ("Modules" :: LText) +++ ppModuleTree pkg qual "n" info ts)
|
|
| 495 | 499 | ppModuleTrees pkg qual tss =
|
| 496 | 500 | divPackageList
|
| 497 | 501 | << ( sectionName
|
| 498 | - << "Packages"
|
|
| 502 | + << ("Packages" :: LText)
|
|
| 499 | 503 | +++ concatHtml
|
| 500 | 504 | [ ppModuleTree pkg qual ("n." ++ show i ++ ".") info ts
|
| 501 | 505 | | (i, (info, ts)) <- zip [(1 :: Int) ..] tss
|
| ... | ... | @@ -519,11 +523,11 @@ mkNode pkg qual ss p (Node s leaf _pkg srcPkg short ts) = |
| 519 | 523 | htmlModule <+> shortDescr +++ htmlPkg +++ subtree
|
| 520 | 524 | where
|
| 521 | 525 | modAttrs = case (ts, leaf) of
|
| 522 | - (_ : _, Nothing) -> collapseControl p "module"
|
|
| 526 | + (_ : _, Nothing) -> collapseControl (LText.pack p) "module"
|
|
| 523 | 527 | (_, _) -> [theclass "module"]
|
| 524 | 528 | |
| 525 | 529 | cBtn = case (ts, leaf) of
|
| 526 | - (_ : _, Just _) -> thespan ! collapseControl p "" << spaceHtml
|
|
| 530 | + (_ : _, Just _) -> thespan ! collapseControl (LText.pack p) "" << spaceHtml
|
|
| 527 | 531 | ([], Just _) -> thespan ! [theclass "noexpander"] << spaceHtml
|
| 528 | 532 | (_, _) -> noHtml
|
| 529 | 533 | -- We only need an explicit collapser button when the module name
|
| ... | ... | @@ -547,11 +551,11 @@ mkNode pkg qual ss p (Node s leaf _pkg srcPkg short ts) = |
| 547 | 551 | then noHtml
|
| 548 | 552 | else
|
| 549 | 553 | collapseDetails
|
| 550 | - p
|
|
| 554 | + (LText.pack p)
|
|
| 551 | 555 | DetailsOpen
|
| 552 | 556 | ( thesummary
|
| 553 | 557 | ! [theclass "hide-when-js-enabled"]
|
| 554 | - << "Submodules"
|
|
| 558 | + << ("Submodules" :: LText)
|
|
| 555 | 559 | +++ mkNodeList pkg qual (s : ss) p ts
|
| 556 | 560 | )
|
| 557 | 561 | |
| ... | ... | @@ -650,10 +654,10 @@ ppJsonIndex odir maybe_source_url maybe_wiki_url unicode pkg qual_opt ifaces ins |
| 650 | 654 | | Just item_html <- processExport True links_info unicode pkg qual item =
|
| 651 | 655 | Just
|
| 652 | 656 | JsonIndexEntry
|
| 653 | - { jieHtmlFragment = showHtmlFragment item_html
|
|
| 657 | + { jieHtmlFragment = Text.unpack (Text.decodeUtf8Lenient (LBS.toStrict (Builder.toLazyByteString (showHtmlFragment item_html))))
|
|
| 654 | 658 | , jieName = unwords (map getOccString names)
|
| 655 | 659 | , jieModule = moduleString mdl
|
| 656 | - , jieLink = fromMaybe "" (listToMaybe (map (nameLink mdl) names))
|
|
| 660 | + , jieLink = LText.unpack $ fromMaybe "" (listToMaybe (map (nameLink mdl) names))
|
|
| 657 | 661 | }
|
| 658 | 662 | | otherwise = Nothing
|
| 659 | 663 | where
|
| ... | ... | @@ -668,7 +672,7 @@ ppJsonIndex odir maybe_source_url maybe_wiki_url unicode pkg qual_opt ifaces ins |
| 668 | 672 | exportName ExportNoDecl{expItemName} = [expItemName]
|
| 669 | 673 | exportName _ = []
|
| 670 | 674 | |
| 671 | - nameLink :: NamedThing name => Module -> name -> String
|
|
| 675 | + nameLink :: NamedThing name => Module -> name -> LText
|
|
| 672 | 676 | nameLink mdl = moduleNameUrl' (moduleName mdl) . nameOccName . getName
|
| 673 | 677 | |
| 674 | 678 | links_info = (maybe_source_url, maybe_wiki_url)
|
| ... | ... | @@ -720,9 +724,9 @@ ppHtmlIndex |
| 720 | 724 | mapM_ (do_sub_index index) initialChars
|
| 721 | 725 | -- Let's add a single large index as well for those who don't know exactly what they're looking for:
|
| 722 | 726 | let mergedhtml = indexPage False Nothing index
|
| 723 | - writeUtf8File (joinPath [odir, subIndexHtmlFile merged_name]) (renderToString debug mergedhtml)
|
|
| 727 | + Builder.writeFile (joinPath [odir, subIndexHtmlFile merged_name]) (renderToBuilder debug mergedhtml)
|
|
| 724 | 728 | |
| 725 | - writeUtf8File (joinPath [odir, indexHtmlFile]) (renderToString debug html)
|
|
| 729 | + Builder.writeFile (joinPath [odir, indexHtmlFile]) (renderToBuilder debug html)
|
|
| 726 | 730 | where
|
| 727 | 731 | indexPage showLetters ch items =
|
| 728 | 732 | headHtml (doctitle ++ " (" ++ indexName ch ++ ")") themes maybe_mathjax_url Nothing
|
| ... | ... | @@ -754,7 +758,7 @@ ppHtmlIndex |
| 754 | 758 | indexInitialLetterLinks =
|
| 755 | 759 | divAlphabet
|
| 756 | 760 | << unordList
|
| 757 | - ( map (\str -> anchor ! [href (subIndexHtmlFile str)] << str) $
|
|
| 761 | + ( map (\str -> anchor ! [href (LText.pack $ subIndexHtmlFile str)] << str) $
|
|
| 758 | 762 | [ [c] | c <- initialChars, any (indexStartsWith c) index
|
| 759 | 763 | ]
|
| 760 | 764 | ++ [merged_name]
|
| ... | ... | @@ -773,7 +777,7 @@ ppHtmlIndex |
| 773 | 777 | |
| 774 | 778 | do_sub_index this_ix c =
|
| 775 | 779 | unless (null index_part) $
|
| 776 | - writeUtf8File (joinPath [odir, subIndexHtmlFile [c]]) (renderToString debug html)
|
|
| 780 | + Builder.writeFile (joinPath [odir, subIndexHtmlFile [c]]) (renderToBuilder debug html)
|
|
| 777 | 781 | where
|
| 778 | 782 | html = indexPage True (Just c) index_part
|
| 779 | 783 | index_part = [(n, stuff) | (n@(headN : _), stuff) <- this_ix, toUpper headN == c]
|
| ... | ... | @@ -844,9 +848,9 @@ ppHtmlIndex |
| 844 | 848 | <-> indexLinks nm entries
|
| 845 | 849 | |
| 846 | 850 | ppAnnot n
|
| 847 | - | not (isValOcc n) = toHtml "Type/Class"
|
|
| 848 | - | isDataOcc n = toHtml "Data Constructor"
|
|
| 849 | - | otherwise = toHtml "Function"
|
|
| 851 | + | not (isValOcc n) = toHtml ("Type/Class" :: LText)
|
|
| 852 | + | isDataOcc n = toHtml ("Data Constructor" :: LText)
|
|
| 853 | + | otherwise = toHtml ("Function" :: LText)
|
|
| 850 | 854 | |
| 851 | 855 | indexLinks nm entries =
|
| 852 | 856 | td
|
| ... | ... | @@ -909,10 +913,10 @@ ppHtmlModule |
| 909 | 913 | mdl_str_linked
|
| 910 | 914 | | ifaceIsSig iface =
|
| 911 | 915 | mdl_str
|
| 912 | - +++ " (signature"
|
|
| 916 | + +++ (" (signature" :: LText)
|
|
| 913 | 917 | +++ sup
|
| 914 | - << ("[" +++ anchor ! [href signatureDocURL] << "?" +++ "]")
|
|
| 915 | - +++ ")"
|
|
| 918 | + << (("[" :: LText) +++ anchor ! [href (LText.pack signatureDocURL)] << ("?" :: LText) +++ ("]" :: LText))
|
|
| 919 | + +++ (")" :: LText)
|
|
| 916 | 920 | | otherwise =
|
| 917 | 921 | toHtml mdl_str
|
| 918 | 922 | real_qual = makeModuleQual qual mdl
|
| ... | ... | @@ -930,7 +934,7 @@ ppHtmlModule |
| 930 | 934 | ]
|
| 931 | 935 | |
| 932 | 936 | createDirectoryIfMissing True odir
|
| 933 | - writeUtf8File (joinPath [odir, moduleHtmlFile mdl]) (renderToString debug html)
|
|
| 937 | + Builder.writeFile (joinPath [odir, moduleHtmlFile mdl]) (renderToBuilder debug html)
|
|
| 934 | 938 | |
| 935 | 939 | signatureDocURL :: String
|
| 936 | 940 | signatureDocURL = "https://wiki.haskell.org/Module_signature"
|
| ... | ... | @@ -965,7 +969,7 @@ ifaceToHtml maybe_source_url maybe_wiki_url iface unicode pkg qual = |
| 965 | 969 | |
| 966 | 970 | description
|
| 967 | 971 | | isNoHtml doc = doc
|
| 968 | - | otherwise = divDescription $ sectionName << "Description" +++ doc
|
|
| 972 | + | otherwise = divDescription $ sectionName << ("Description" :: LText) +++ doc
|
|
| 969 | 973 | where
|
| 970 | 974 | doc = docSection Nothing pkg qual (ifaceRnDoc iface)
|
| 971 | 975 | |
| ... | ... | @@ -978,7 +982,7 @@ ifaceToHtml maybe_source_url maybe_wiki_url iface unicode pkg qual = |
| 978 | 982 | "syn"
|
| 979 | 983 | DetailsClosed
|
| 980 | 984 | ( thesummary
|
| 981 | - << "Synopsis"
|
|
| 985 | + << ("Synopsis" :: LText)
|
|
| 982 | 986 | +++ shortDeclList
|
| 983 | 987 | ( mapMaybe (processExport True linksInfo unicode pkg qual) exports
|
| 984 | 988 | )
|
| ... | ... | @@ -991,7 +995,7 @@ ifaceToHtml maybe_source_url maybe_wiki_url iface unicode pkg qual = |
| 991 | 995 | case exports of
|
| 992 | 996 | [] -> noHtml
|
| 993 | 997 | ExportGroup{} : _ -> noHtml
|
| 994 | - _ -> h1 << "Documentation"
|
|
| 998 | + _ -> h1 << ("Documentation" :: LText)
|
|
| 995 | 999 | |
| 996 | 1000 | bdy =
|
| 997 | 1001 | foldr (+++) noHtml $
|
| ... | ... | @@ -1017,7 +1021,7 @@ ppModuleContents pkg qual exports orphan |
| 1017 | 1021 | contentsDiv =
|
| 1018 | 1022 | divTableOfContents
|
| 1019 | 1023 | << ( divContentsList
|
| 1020 | - << ( (sectionName << "Contents")
|
|
| 1024 | + << ( (sectionName << ("Contents" :: LText))
|
|
| 1021 | 1025 | ! [strAttr "onclick" "window.scrollTo(0,0)"]
|
| 1022 | 1026 | +++ unordList (sections ++ orphanSection)
|
| 1023 | 1027 | )
|
| ... | ... | @@ -1025,7 +1029,7 @@ ppModuleContents pkg qual exports orphan |
| 1025 | 1029 | |
| 1026 | 1030 | (sections, _leftovers {-should be []-}) = process 0 exports
|
| 1027 | 1031 | orphanSection
|
| 1028 | - | orphan = [linkedAnchor "section.orphans" << "Orphan instances"]
|
|
| 1032 | + | orphan = [linkedAnchor "section.orphans" << ("Orphan instances" :: LText)]
|
|
| 1029 | 1033 | | otherwise = []
|
| 1030 | 1034 | |
| 1031 | 1035 | process :: Int -> [ExportItem DocNameI] -> ([Html], [ExportItem DocNameI])
|
| ... | ... | @@ -1035,7 +1039,7 @@ ppModuleContents pkg qual exports orphan |
| 1035 | 1039 | | otherwise = (html : secs, rest2)
|
| 1036 | 1040 | where
|
| 1037 | 1041 | html =
|
| 1038 | - linkedAnchor (groupId id0)
|
|
| 1042 | + linkedAnchor (groupId (LText.pack id0))
|
|
| 1039 | 1043 | << docToHtmlNoAnchors (Just id0) pkg qual (mkMeta doc)
|
| 1040 | 1044 | +++ mk_subsections ssecs
|
| 1041 | 1045 | (ssecs, rest1) = process lev rest
|
| ... | ... | @@ -1103,7 +1107,7 @@ processExport |
| 1103 | 1107 | ) =
|
| 1104 | 1108 | processDecl summary $ ppDecl summary links decl pats doc insts fixities subdocs splice unicode pkg qual
|
| 1105 | 1109 | processExport summary _ _ pkg qual (ExportGroup lev id0 doc) =
|
| 1106 | - nothingIf summary $ groupHeading lev id0 << docToHtmlNoAnchors (Just id0) pkg qual (mkMeta doc)
|
|
| 1110 | + nothingIf summary $ groupHeading lev (LText.pack id0) << docToHtmlNoAnchors (Just id0) pkg qual (mkMeta doc)
|
|
| 1107 | 1111 | processExport summary _ _ _ qual (ExportNoDecl y []) =
|
| 1108 | 1112 | processDeclOneLiner summary $ ppDocName qual Prefix True y
|
| 1109 | 1113 | processExport summary _ _ _ qual (ExportNoDecl y subs) =
|
| ... | ... | @@ -1113,7 +1117,7 @@ processExport summary _ _ _ qual (ExportNoDecl y subs) = |
| 1113 | 1117 | processExport summary _ _ pkg qual (ExportDoc doc) =
|
| 1114 | 1118 | nothingIf summary $ docSection_ Nothing pkg qual doc
|
| 1115 | 1119 | processExport summary _ _ _ _ (ExportModule mdl) =
|
| 1116 | - processDeclOneLiner summary $ toHtml "module" <+> ppModule mdl
|
|
| 1120 | + processDeclOneLiner summary $ toHtml ("module" :: LText) <+> ppModule mdl
|
|
| 1117 | 1121 | |
| 1118 | 1122 | nothingIf :: Bool -> a -> Maybe a
|
| 1119 | 1123 | nothingIf True _ = Nothing
|
| ... | ... | @@ -1132,7 +1136,7 @@ processDeclOneLiner :: Bool -> Html -> Maybe Html |
| 1132 | 1136 | processDeclOneLiner True = Just
|
| 1133 | 1137 | processDeclOneLiner False = Just . divTopDecl . declElem
|
| 1134 | 1138 | |
| 1135 | -groupHeading :: Int -> String -> Html -> Html
|
|
| 1139 | +groupHeading :: Int -> LText -> Html -> Html
|
|
| 1136 | 1140 | groupHeading lev id0 = linkedAnchor grpId . groupTag lev ! [identifier grpId]
|
| 1137 | 1141 | where
|
| 1138 | 1142 | grpId = groupId id0
|
| ... | ... | @@ -45,6 +45,7 @@ import Haddock.Backends.Xhtml.Utils |
| 45 | 45 | import Haddock.Doc (combineDocumentation)
|
| 46 | 46 | import Haddock.GhcUtils
|
| 47 | 47 | import Haddock.Types
|
| 48 | +import qualified Data.Text.Lazy as LText
|
|
| 48 | 49 | |
| 49 | 50 | -- | Pretty print a declaration
|
| 50 | 51 | ppDecl
|
| ... | ... | @@ -352,9 +353,9 @@ ppSubSigLike unicode qual typ argDocs subdocs sep emptyCtxts = do_sig_args 0 sep |
| 352 | 353 | -- We need 'gadtComma' and 'gadtEnd' to line up with the `{` from
|
| 353 | 354 | -- 'gadtOpen', so we add 3 spaces to cover for `-> `/`:: ` (3 in unicode
|
| 354 | 355 | -- mode since `->` and `::` are rendered as single characters.
|
| 355 | - gadtComma = concatHtml (replicate (if unicode then 2 else 3) spaceHtml) <> toHtml ","
|
|
| 356 | - gadtEnd = concatHtml (replicate (if unicode then 2 else 3) spaceHtml) <> toHtml "}"
|
|
| 357 | - gadtOpen = toHtml "{"
|
|
| 356 | + gadtComma = concatHtml (replicate (if unicode then 2 else 3) spaceHtml) <> toHtml ("," :: LText)
|
|
| 357 | + gadtEnd = concatHtml (replicate (if unicode then 2 else 3) spaceHtml) <> toHtml ("}" :: LText)
|
|
| 358 | + gadtOpen = toHtml ("{" :: LText)
|
|
| 358 | 359 | |
| 359 | 360 | ppFixities :: [(DocName, Fixity)] -> Qualification -> Html
|
| 360 | 361 | ppFixities [] _ = noHtml
|
| ... | ... | @@ -365,7 +366,7 @@ ppFixities fs qual = foldr1 (+++) (map ppFix uniq_fs) +++ rightEdge |
| 365 | 366 | ! [theclass "fixity"]
|
| 366 | 367 | << (toHtml d <+> toHtml (show p) <+> ppNames ns)
|
| 367 | 368 | |
| 368 | - ppDir InfixR = "infixr"
|
|
| 369 | + ppDir InfixR = ("infixr" :: LText)
|
|
| 369 | 370 | ppDir InfixL = "infixl"
|
| 370 | 371 | ppDir InfixN = "infix"
|
| 371 | 372 | |
| ... | ... | @@ -730,7 +731,7 @@ ppContextNoLocsMaybe :: [HsType DocNameI] -> Unicode -> Qualification -> HideEmp |
| 730 | 731 | ppContextNoLocsMaybe [] _ _ emptyCtxts =
|
| 731 | 732 | case emptyCtxts of
|
| 732 | 733 | HideEmptyContexts -> Nothing
|
| 733 | - ShowEmptyToplevelContexts -> Just (toHtml "()")
|
|
| 734 | + ShowEmptyToplevelContexts -> Just (toHtml ("()" :: LText))
|
|
| 734 | 735 | ppContextNoLocsMaybe cxt unicode qual _ = Just $ ppHsContext cxt unicode qual
|
| 735 | 736 | |
| 736 | 737 | ppContext :: HsContext DocNameI -> Unicode -> Qualification -> HideEmptyContexts -> Html
|
| ... | ... | @@ -1006,13 +1007,13 @@ ppClassDecl |
| 1006 | 1007 | == [getName n' | ClassOpSig _ _ ns _ <- sigs, L _ n' <- ns] ->
|
| 1007 | 1008 | noHtml
|
| 1008 | 1009 | -- Minimal complete definition = nothing
|
| 1009 | - And [] : _ -> subMinimal $ toHtml "Nothing"
|
|
| 1010 | + And [] : _ -> subMinimal $ toHtml ("Nothing" :: LText)
|
|
| 1010 | 1011 | m : _ -> subMinimal $ ppMinimal False m
|
| 1011 | 1012 | _ -> noHtml
|
| 1012 | 1013 | |
| 1013 | 1014 | ppMinimal _ (Var (L _ n)) = ppDocName qual Prefix True n
|
| 1014 | - ppMinimal _ (And fs) = foldr1 (\a b -> a +++ ", " +++ b) $ map (ppMinimal True . unLoc) fs
|
|
| 1015 | - ppMinimal p (Or fs) = wrap $ foldr1 (\a b -> a +++ " | " +++ b) $ map (ppMinimal False . unLoc) fs
|
|
| 1015 | + ppMinimal _ (And fs) = foldr1 (\a b -> a +++ (", " :: LText) +++ b) $ map (ppMinimal True . unLoc) fs
|
|
| 1016 | + ppMinimal p (Or fs) = wrap $ foldr1 (\a b -> a +++ (" | " :: LText) +++ b) $ map (ppMinimal False . unLoc) fs
|
|
| 1016 | 1017 | where
|
| 1017 | 1018 | wrap | p = parens | otherwise = id
|
| 1018 | 1019 | ppMinimal p (Parens x) = ppMinimal p (unLoc x)
|
| ... | ... | @@ -1115,7 +1116,7 @@ ppInstHead links splice unicode qual mdoc origin orphan no ihd@(InstHead{..}) md |
| 1115 | 1116 | pdecl = pdata <+> ppShortDataDecl False True dd [] unicode qual
|
| 1116 | 1117 | DataInst {} -> error "ppInstHead"
|
| 1117 | 1118 | where
|
| 1118 | - mname = maybe noHtml (\m -> toHtml "Defined in" <+> ppModule m) mdl
|
|
| 1119 | + mname = maybe noHtml (\m -> toHtml ("Defined in" :: LText) <+> ppModule m) mdl
|
|
| 1119 | 1120 | iid = instanceId origin no orphan ihd
|
| 1120 | 1121 | typ = ppAppNameTypes ihdClsName ihdTypes unicode qual
|
| 1121 | 1122 | |
| ... | ... | @@ -1163,9 +1164,9 @@ ppInstanceSigs links splice unicode qual sigs = do |
| 1163 | 1164 | lookupAnySubdoc :: Eq id1 => id1 -> [(id1, DocForDecl id2)] -> DocForDecl id2
|
| 1164 | 1165 | lookupAnySubdoc n = Maybe.fromMaybe noDocForDecl . lookup n
|
| 1165 | 1166 | |
| 1166 | -instanceId :: InstOrigin DocName -> Int -> Bool -> InstHead DocNameI -> String
|
|
| 1167 | +instanceId :: InstOrigin DocName -> Int -> Bool -> InstHead DocNameI -> LText
|
|
| 1167 | 1168 | instanceId origin no orphan ihd =
|
| 1168 | - concat $
|
|
| 1169 | + LText.pack $ concat $
|
|
| 1169 | 1170 | ["o:" | orphan]
|
| 1170 | 1171 | ++ [ qual origin
|
| 1171 | 1172 | , ":" ++ getOccString origin
|
| ... | ... | @@ -1529,7 +1530,7 @@ ppConstrHdr forall_ tvs ctxt unicode qual = ppForall +++ ppCtxt |
| 1529 | 1530 | | otherwise =
|
| 1530 | 1531 | ppContextNoArrow ctxt unicode qual HideEmptyContexts
|
| 1531 | 1532 | <+> darrow unicode
|
| 1532 | - +++ toHtml " "
|
|
| 1533 | + +++ toHtml (" " :: LText)
|
|
| 1533 | 1534 | |
| 1534 | 1535 | -- | Pretty-print a record field
|
| 1535 | 1536 | ppSideBySideField
|
| ... | ... | @@ -1564,7 +1565,7 @@ ppSideBySideField subdocs unicode qual (HsConDeclRecField _ names ltype) = |
| 1564 | 1565 | ppRecFieldMultAnn :: Unicode -> Qualification -> HsConDeclField DocNameI -> Html
|
| 1565 | 1566 | ppRecFieldMultAnn unicode qual (CDF { cdf_multiplicity = ann }) = case ann of
|
| 1566 | 1567 | HsUnannotated _ -> noHtml
|
| 1567 | - HsLinearAnn _ -> toHtml "%1"
|
|
| 1568 | + HsLinearAnn _ -> toHtml ("%1" :: LText)
|
|
| 1568 | 1569 | HsExplicitMult _ mult -> multAnnotation <> ppr_mono_lty mult unicode qual HideEmptyContexts
|
| 1569 | 1570 | |
| 1570 | 1571 | ppShortField :: Bool -> Unicode -> Qualification -> HsConDeclRecField DocNameI -> Html
|
| ... | ... | @@ -1668,8 +1669,8 @@ ppDataHeader _ _ _ _ = error "ppDataHeader: illegal argument" |
| 1668 | 1669 | --------------------------------------------------------------------------------
|
| 1669 | 1670 | |
| 1670 | 1671 | ppBang :: HsSrcBang -> Html
|
| 1671 | -ppBang (HsSrcBang _ _ SrcStrict) = toHtml "!"
|
|
| 1672 | -ppBang (HsSrcBang _ _ SrcLazy) = toHtml "~"
|
|
| 1672 | +ppBang (HsSrcBang _ _ SrcStrict) = toHtml ("!" :: LText)
|
|
| 1673 | +ppBang (HsSrcBang _ _ SrcLazy) = toHtml ("~" :: LText)
|
|
| 1673 | 1674 | ppBang _ = noHtml
|
| 1674 | 1675 | |
| 1675 | 1676 | tupleParens :: HsTupleSort -> [Html] -> Html
|
| ... | ... | @@ -1707,7 +1708,7 @@ ppSigType unicode qual emptyCtxts sig_ty = ppr_sig_ty (reparenSigType sig_ty) un |
| 1707 | 1708 | ppLHsTypeArg :: Unicode -> Qualification -> HideEmptyContexts -> LHsTypeArg DocNameI -> Html
|
| 1708 | 1709 | ppLHsTypeArg unicode qual emptyCtxts (HsValArg _ ty) = ppLParendType unicode qual emptyCtxts ty
|
| 1709 | 1710 | ppLHsTypeArg unicode qual emptyCtxts (HsTypeArg _ ki) = atSign <> ppLParendType unicode qual emptyCtxts ki
|
| 1710 | -ppLHsTypeArg _ _ _ (HsArgPar _) = toHtml ""
|
|
| 1711 | +ppLHsTypeArg _ _ _ (HsArgPar _) = toHtml ("" :: LText)
|
|
| 1711 | 1712 | |
| 1712 | 1713 | class RenderableBndrFlag flag where
|
| 1713 | 1714 | ppHsTyVarBndr :: Unicode -> Qualification -> HsTyVarBndr flag DocNameI -> Html
|
| ... | ... | @@ -1814,12 +1815,12 @@ ppr_mono_ty (HsQualTy _ ctxt ty) unicode qual emptyCtxts = |
| 1814 | 1815 | ppLContext (Just ctxt) unicode qual emptyCtxts <+> ppr_mono_lty ty unicode qual emptyCtxts
|
| 1815 | 1816 | -- UnicodeSyntax alternatives
|
| 1816 | 1817 | ppr_mono_ty (HsTyVar _ _ (L _ name)) True _ _
|
| 1817 | - | getOccString (getName name) == "(->)" = toHtml "(→)"
|
|
| 1818 | + | getOccString (getName name) == "(->)" = toHtml ("(→)" :: LText)
|
|
| 1818 | 1819 | ppr_mono_ty (HsTyVar _ prom (L _ name)) _ q _
|
| 1819 | 1820 | | isPromoted prom = promoQuote (ppDocName q Prefix True name)
|
| 1820 | 1821 | | otherwise = ppDocName q Prefix True name
|
| 1821 | 1822 | ppr_mono_ty (HsStarTy _ isUni) u _ _ =
|
| 1822 | - toHtml (if u || isUni then "★" else "*")
|
|
| 1823 | + toHtml (if u || isUni then "★" else "*" :: LText)
|
|
| 1823 | 1824 | ppr_mono_ty (HsFunTy _ mult ty1 ty2) u q e =
|
| 1824 | 1825 | hsep
|
| 1825 | 1826 | [ ppr_mono_lty ty1 u q HideEmptyContexts
|
| ... | ... | @@ -1842,7 +1843,7 @@ ppr_mono_ty (HsIParamTy _ (L _ n) ty) u q _ = |
| 1842 | 1843 | ppr_mono_ty (HsSpliceTy v _) _ _ _ = dataConCantHappen v
|
| 1843 | 1844 | ppr_mono_ty (XHsType (HsBangTy b ty)) u q _ =
|
| 1844 | 1845 | ppBang b +++ ppLParendType u q HideEmptyContexts ty
|
| 1845 | -ppr_mono_ty (XHsType (HsRecTy{})) _ _ _ = toHtml "{..}"
|
|
| 1846 | +ppr_mono_ty (XHsType (HsRecTy{})) _ _ _ = toHtml ("{..}" :: LText)
|
|
| 1846 | 1847 | -- Can now legally occur in ConDeclGADT, the output here is to provide a
|
| 1847 | 1848 | -- placeholder in the signature, which is followed by the field
|
| 1848 | 1849 | -- declarations.
|
| ... | ... | @@ -39,6 +39,7 @@ import Haddock.Doc |
| 39 | 39 | )
|
| 40 | 40 | import Haddock.Types
|
| 41 | 41 | import Haddock.Utils
|
| 42 | +import qualified Data.Text.Lazy as LText
|
|
| 42 | 43 | |
| 43 | 44 | parHtmlMarkup
|
| 44 | 45 | :: Qualification
|
| ... | ... | @@ -60,7 +61,7 @@ parHtmlMarkup qual insertAnchors ppId = |
| 60 | 61 | mdl' = case reverse mdl of
|
| 61 | 62 | '\\' : _ -> init mdl
|
| 62 | 63 | _ -> mdl
|
| 63 | - in ppModuleRef lbl (mkModuleName mdl') ref
|
|
| 64 | + in ppModuleRef lbl (mkModuleName mdl') (LText.pack ref)
|
|
| 64 | 65 | , markupWarning = thediv ! [theclass "warning"]
|
| 65 | 66 | , markupEmphasis = emphasize
|
| 66 | 67 | , markupBold = strong
|
| ... | ... | @@ -73,14 +74,14 @@ parHtmlMarkup qual insertAnchors ppId = |
| 73 | 74 | if insertAnchors
|
| 74 | 75 | then
|
| 75 | 76 | anchor
|
| 76 | - ! [href url]
|
|
| 77 | + ! [href (LText.pack url)]
|
|
| 77 | 78 | << fromMaybe (toHtml url) mLabel
|
| 78 | 79 | else fromMaybe (toHtml url) mLabel
|
| 79 | 80 | , markupAName = \aname ->
|
| 80 | 81 | if insertAnchors
|
| 81 | - then namedAnchor aname << ""
|
|
| 82 | + then namedAnchor (LText.pack aname) << ("" :: LText.Text)
|
|
| 82 | 83 | else noHtml
|
| 83 | - , markupPic = \(Picture uri t) -> image ! ([src uri] ++ fromMaybe [] (return . title <$> t))
|
|
| 84 | + , markupPic = \(Picture uri t) -> image ! ([src (LText.pack uri)] ++ fromMaybe [] (return . title <$> (LText.pack <$> t)))
|
|
| 84 | 85 | , markupMathInline = \mathjax -> thespan ! [theclass "mathjax"] << toHtml ("\\(" ++ mathjax ++ "\\)")
|
| 85 | 86 | , markupMathDisplay = \mathjax -> thespan ! [theclass "mathjax"] << toHtml ("\\[" ++ mathjax ++ "\\]")
|
| 86 | 87 | , markupProperty = pre . toHtml
|
| ... | ... | @@ -121,7 +122,7 @@ parHtmlMarkup qual insertAnchors ppId = |
| 121 | 122 | exampleToHtml (Example expression result) = htmlExample
|
| 122 | 123 | where
|
| 123 | 124 | htmlExample = htmlPrompt +++ htmlExpression +++ toHtml (unlines result)
|
| 124 | - htmlPrompt = (thecode . toHtml $ ">>> ") ! [theclass "prompt"]
|
|
| 125 | + htmlPrompt = (thecode . toHtml $ (">>> " :: LText.Text)) ! [theclass "prompt"]
|
|
| 125 | 126 | htmlExpression = (strong . thecode . toHtml $ expression ++ "\n") ! [theclass "userinput"]
|
| 126 | 127 | |
| 127 | 128 | makeOrdList :: HTML a => [(Int, a)] -> Html
|
| ... | ... | @@ -204,9 +205,9 @@ hackMarkup fmt' currPkg h' = |
| 204 | 205 | hackMarkup' fmt h = case h of
|
| 205 | 206 | UntouchedDoc d -> (markup fmt $ _doc d, [_meta d])
|
| 206 | 207 | CollapsingHeader (Header lvl titl) par n nm ->
|
| 207 | - let id_ = makeAnchorId $ "ch:" ++ fromMaybe "noid:" nm ++ show n
|
|
| 208 | + let id_ = makeAnchorId $ "ch:" <> fromMaybe "noid:" (LText.pack <$> nm) <> LText.pack (show n)
|
|
| 208 | 209 | col' = collapseControl id_ "subheading"
|
| 209 | - summary = thesummary ! [theclass "hide-when-js-enabled"] << "Expand"
|
|
| 210 | + summary = thesummary ! [theclass "hide-when-js-enabled"] << ("Expand" :: LText.Text)
|
|
| 210 | 211 | instTable contents = collapseDetails id_ DetailsClosed (summary +++ contents)
|
| 211 | 212 | lvs = zip [1 ..] [h1, h2, h3, h4, h5, h6]
|
| 212 | 213 | getHeader = fromMaybe caption (lookup lvl lvs)
|
| ... | ... | @@ -63,6 +63,7 @@ import Haddock.Backends.Xhtml.Types |
| 63 | 63 | import Haddock.Backends.Xhtml.Utils
|
| 64 | 64 | import Haddock.Types
|
| 65 | 65 | import Haddock.Utils (makeAnchorId, nameAnchorId)
|
| 66 | +import qualified Data.Text.Lazy as LText
|
|
| 66 | 67 | |
| 67 | 68 | --------------------------------------------------------------------------------
|
| 68 | 69 | |
| ... | ... | @@ -73,7 +74,7 @@ import Haddock.Utils (makeAnchorId, nameAnchorId) |
| 73 | 74 | miniBody :: Html -> Html
|
| 74 | 75 | miniBody = body ! [identifier "mini"]
|
| 75 | 76 | |
| 76 | -sectionDiv :: String -> Html -> Html
|
|
| 77 | +sectionDiv :: LText -> Html -> Html
|
|
| 77 | 78 | sectionDiv i = thediv ! [identifier i]
|
| 78 | 79 | |
| 79 | 80 | sectionName :: Html -> Html
|
| ... | ... | @@ -138,11 +139,11 @@ divTopDecl = thediv ! [theclass "top"] |
| 138 | 139 | |
| 139 | 140 | type SubDecl = (Html, Maybe (MDoc DocName), [Html])
|
| 140 | 141 | |
| 141 | -divSubDecls :: HTML a => String -> a -> Maybe Html -> Html
|
|
| 142 | +divSubDecls :: LText -> LText -> Maybe Html -> Html
|
|
| 142 | 143 | divSubDecls cssClass captionName = maybe noHtml wrap
|
| 143 | 144 | where
|
| 144 | 145 | wrap = (subSection <<) . (subCaption +++)
|
| 145 | - subSection = thediv ! [theclass $ unwords ["subs", cssClass]]
|
|
| 146 | + subSection = thediv ! [theclass $ LText.unwords ["subs", cssClass]]
|
|
| 146 | 147 | subCaption = paragraph ! [theclass "caption"] << captionName
|
| 147 | 148 | |
| 148 | 149 | subDlist :: Maybe Package -> Qualification -> [SubDecl] -> Maybe Html
|
| ... | ... | @@ -232,9 +233,9 @@ subInstances pkg qual nm lnks splice = maybe noHtml wrap . instTable |
| 232 | 233 | wrap contents = subSection (hdr +++ collapseDetails id_ DetailsOpen (summary +++ contents))
|
| 233 | 234 | instTable = subTableSrc pkg qual lnks splice
|
| 234 | 235 | subSection = thediv ! [theclass "subs instances"]
|
| 235 | - hdr = h4 ! collapseControl id_ "instances" << "Instances"
|
|
| 236 | - summary = thesummary ! [theclass "hide-when-js-enabled"] << "Instances details"
|
|
| 237 | - id_ = makeAnchorId $ "i:" ++ nm
|
|
| 236 | + hdr = h4 ! collapseControl id_ "instances" << ("Instances" :: LText)
|
|
| 237 | + summary = thesummary ! [theclass "hide-when-js-enabled"] << ("Instances details" :: LText)
|
|
| 238 | + id_ = makeAnchorId $ "i:" <> (LText.pack nm)
|
|
| 238 | 239 | |
| 239 | 240 | subOrphanInstances
|
| 240 | 241 | :: Maybe Package
|
| ... | ... | @@ -245,12 +246,12 @@ subOrphanInstances |
| 245 | 246 | -> Html
|
| 246 | 247 | subOrphanInstances pkg qual lnks splice = maybe noHtml wrap . instTable
|
| 247 | 248 | where
|
| 248 | - wrap = ((h1 << "Orphan instances") +++)
|
|
| 249 | - instTable = fmap (thediv ! [identifier ("section." ++ id_)] <<) . subTableSrc pkg qual lnks splice
|
|
| 249 | + wrap = ((h1 << ("Orphan instances" :: LText)) +++)
|
|
| 250 | + instTable = fmap (thediv ! [identifier ("section." <> id_)] <<) . subTableSrc pkg qual lnks splice
|
|
| 250 | 251 | id_ = makeAnchorId "orphans"
|
| 251 | 252 | |
| 252 | 253 | subInstHead
|
| 253 | - :: String
|
|
| 254 | + :: LText
|
|
| 254 | 255 | -- ^ Instance unique id (for anchor generation)
|
| 255 | 256 | -> Html
|
| 256 | 257 | -- ^ Header content (instance name and type)
|
| ... | ... | @@ -261,7 +262,7 @@ subInstHead iid hdr = |
| 261 | 262 | expander = thespan ! collapseControl (instAnchorId iid) "instance"
|
| 262 | 263 | |
| 263 | 264 | subInstDetails
|
| 264 | - :: String
|
|
| 265 | + :: LText
|
|
| 265 | 266 | -- ^ Instance unique id (for anchor generation)
|
| 266 | 267 | -> [Html]
|
| 267 | 268 | -- ^ Associated type contents
|
| ... | ... | @@ -274,7 +275,7 @@ subInstDetails iid ats mets mdl = |
| 274 | 275 | subInstSection iid << (p mdl <+> subAssociatedTypes ats <+> subMethods mets)
|
| 275 | 276 | |
| 276 | 277 | subFamInstDetails
|
| 277 | - :: String
|
|
| 278 | + :: LText
|
|
| 278 | 279 | -- ^ Instance unique id (for anchor generation)
|
| 279 | 280 | -> Html
|
| 280 | 281 | -- ^ Type or data family instance
|
| ... | ... | @@ -285,16 +286,16 @@ subFamInstDetails iid fi mdl = |
| 285 | 286 | subInstSection iid << (p mdl <+> (thediv ! [theclass "src"] << fi))
|
| 286 | 287 | |
| 287 | 288 | subInstSection
|
| 288 | - :: String
|
|
| 289 | + :: LText
|
|
| 289 | 290 | -- ^ Instance unique id (for anchor generation)
|
| 290 | 291 | -> Html
|
| 291 | 292 | -> Html
|
| 292 | 293 | subInstSection iid contents = collapseDetails (instAnchorId iid) DetailsClosed (summary +++ contents)
|
| 293 | 294 | where
|
| 294 | - summary = thesummary ! [theclass "hide-when-js-enabled"] << "Instance details"
|
|
| 295 | + summary = thesummary ! [theclass "hide-when-js-enabled"] << ("Instance details" :: LText)
|
|
| 295 | 296 | |
| 296 | -instAnchorId :: String -> String
|
|
| 297 | -instAnchorId iid = makeAnchorId $ "i:" ++ iid
|
|
| 297 | +instAnchorId :: LText -> LText
|
|
| 298 | +instAnchorId iid = makeAnchorId $ "i:" <> iid
|
|
| 298 | 299 | |
| 299 | 300 | subMethods :: [Html] -> Html
|
| 300 | 301 | subMethods = divSubDecls "methods" "Methods" . subBlock
|
| ... | ... | @@ -321,7 +322,7 @@ topDeclElem lnks loc splice name html = |
| 321 | 322 | -- Name must be documented, otherwise we wouldn't get here.
|
| 322 | 323 | links :: LinksInfo -> SrcSpan -> Bool -> Maybe Module -> DocName -> Html
|
| 323 | 324 | links ((_, _, sourceMap, lineMap), (_, _, maybe_wiki_url)) loc splice mdl' docName@(Documented n mdl) =
|
| 324 | - srcLink <+> wikiLink <+> (selfLink ! [theclass "selflink"] << "#")
|
|
| 325 | + srcLink <+> wikiLink <+> (selfLink ! [theclass "selflink"] << ("#" :: LText))
|
|
| 325 | 326 | where
|
| 326 | 327 | selfLink = linkedAnchor (nameAnchorId (nameOccName (getName docName)))
|
| 327 | 328 | |
| ... | ... | @@ -335,15 +336,15 @@ links ((_, _, sourceMap, lineMap), (_, _, maybe_wiki_url)) loc splice mdl' docNa |
| 335 | 336 | in case mUrl of
|
| 336 | 337 | Nothing -> noHtml
|
| 337 | 338 | Just url ->
|
| 338 | - let url' = spliceURL (Just origMod) (Just n) (Just loc) url
|
|
| 339 | - in anchor ! [href url', theclass "link"] << "Source"
|
|
| 339 | + let url' = LText.pack $ spliceURL (Just origMod) (Just n) (Just loc) url
|
|
| 340 | + in anchor ! [href url', theclass "link"] << ("Source" :: LText)
|
|
| 340 | 341 | |
| 341 | 342 | wikiLink =
|
| 342 | 343 | case maybe_wiki_url of
|
| 343 | 344 | Nothing -> noHtml
|
| 344 | 345 | Just url ->
|
| 345 | - let url' = spliceURL (Just mdl) (Just n) (Just loc) url
|
|
| 346 | - in anchor ! [href url', theclass "link"] << "Comments"
|
|
| 346 | + let url' = LText.pack $ spliceURL (Just mdl) (Just n) (Just loc) url
|
|
| 347 | + in anchor ! [href url', theclass "link"] << ("Comments" :: LText)
|
|
| 347 | 348 | |
| 348 | 349 | -- For source links, we want to point to the original module,
|
| 349 | 350 | -- because only that will have the source.
|
| ... | ... | @@ -41,6 +41,7 @@ import Haddock.Backends.Xhtml.Utils |
| 41 | 41 | import Haddock.GhcUtils
|
| 42 | 42 | import Haddock.Types
|
| 43 | 43 | import Haddock.Utils
|
| 44 | +import qualified Data.Text.Lazy as LText
|
|
| 44 | 45 | |
| 45 | 46 | -- | Indicator of how to render a 'DocName' into 'Html'
|
| 46 | 47 | data Notation
|
| ... | ... | @@ -171,7 +172,7 @@ linkIdOcc mdl mbName insertAnchors = |
| 171 | 172 | then anchor ! [href url, title ttl]
|
| 172 | 173 | else id
|
| 173 | 174 | where
|
| 174 | - ttl = moduleNameString (moduleName mdl)
|
|
| 175 | + ttl = LText.pack (moduleNameString (moduleName mdl))
|
|
| 175 | 176 | url = case mbName of
|
| 176 | 177 | Nothing -> moduleUrl mdl
|
| 177 | 178 | Just name -> moduleNameUrl mdl name
|
| ... | ... | @@ -179,9 +180,9 @@ linkIdOcc mdl mbName insertAnchors = |
| 179 | 180 | linkIdOcc' :: ModuleName -> Maybe OccName -> Html -> Html
|
| 180 | 181 | linkIdOcc' mdl mbName = anchor ! [href url, title ttl]
|
| 181 | 182 | where
|
| 182 | - ttl = moduleNameString mdl
|
|
| 183 | + ttl = LText.pack (moduleNameString mdl)
|
|
| 183 | 184 | url = case mbName of
|
| 184 | - Nothing -> moduleHtmlFile' mdl
|
|
| 185 | + Nothing -> LText.pack (moduleHtmlFile' mdl)
|
|
| 185 | 186 | Just name -> moduleNameUrl' mdl name
|
| 186 | 187 | |
| 187 | 188 | ppModule :: Module -> Html
|
| ... | ... | @@ -190,14 +191,14 @@ ppModule mdl = |
| 190 | 191 | ! [href (moduleUrl mdl)]
|
| 191 | 192 | << toHtml (moduleString mdl)
|
| 192 | 193 | |
| 193 | -ppModuleRef :: Maybe Html -> ModuleName -> String -> Html
|
|
| 194 | +ppModuleRef :: Maybe Html -> ModuleName -> LText -> Html
|
|
| 194 | 195 | ppModuleRef Nothing mdl ref =
|
| 195 | 196 | anchor
|
| 196 | - ! [href (moduleHtmlFile' mdl ++ ref)]
|
|
| 197 | + ! [href (LText.pack (moduleHtmlFile' mdl) <> ref)]
|
|
| 197 | 198 | << toHtml (moduleNameString mdl)
|
| 198 | 199 | ppModuleRef (Just lbl) mdl ref =
|
| 199 | 200 | anchor
|
| 200 | - ! [href (moduleHtmlFile' mdl ++ ref)]
|
|
| 201 | + ! [href (LText.pack (moduleHtmlFile' mdl) <> ref)]
|
|
| 201 | 202 | << lbl
|
| 202 | 203 | |
| 203 | 204 | -- NB: The ref parameter already includes the '#'.
|
| ... | ... | @@ -27,6 +27,7 @@ import System.Directory |
| 27 | 27 | import System.FilePath
|
| 28 | 28 | import Text.XHtml hiding (name, p, quote, title, (</>))
|
| 29 | 29 | import qualified Text.XHtml as XHtml
|
| 30 | +import qualified Data.Text.Lazy as LText
|
|
| 30 | 31 | |
| 31 | 32 | import Haddock.Backends.Xhtml.Types (BaseURL, withBaseURL)
|
| 32 | 33 | import Haddock.Options
|
| ... | ... | @@ -185,10 +186,10 @@ styleSheet base_url ts = toHtml $ zipWith mkLink rels ts |
| 185 | 186 | rels = "stylesheet" : repeat "alternate stylesheet"
|
| 186 | 187 | mkLink aRel t =
|
| 187 | 188 | thelink
|
| 188 | - ! [ href (withBaseURL base_url (themeHref t))
|
|
| 189 | + ! [ href (LText.pack (withBaseURL base_url (themeHref t)))
|
|
| 189 | 190 | , rel aRel
|
| 190 | 191 | , thetype "text/css"
|
| 191 | - , XHtml.title (themeName t)
|
|
| 192 | + , XHtml.title (LText.pack (themeName t))
|
|
| 192 | 193 | ]
|
| 193 | 194 | << noHtml
|
| 194 | 195 |
| ... | ... | @@ -13,7 +13,7 @@ |
| 13 | 13 | -- Stability : experimental
|
| 14 | 14 | -- Portability : portable
|
| 15 | 15 | module Haddock.Backends.Xhtml.Utils
|
| 16 | - ( renderToString
|
|
| 16 | + ( renderToBuilder
|
|
| 17 | 17 | , namedAnchor
|
| 18 | 18 | , linkedAnchor
|
| 19 | 19 | , spliceURL
|
| ... | ... | @@ -58,6 +58,7 @@ import GHC.Types.Name (getOccString, isValOcc, nameOccName) |
| 58 | 58 | import GHC.Unit.Module (Module, ModuleName, moduleName, moduleNameString)
|
| 59 | 59 | import Text.XHtml hiding (name, p, quote, title)
|
| 60 | 60 | import qualified Text.XHtml as XHtml
|
| 61 | +import qualified Data.Text.Lazy as LText
|
|
| 61 | 62 | |
| 62 | 63 | import Haddock.Utils
|
| 63 | 64 | |
| ... | ... | @@ -118,8 +119,8 @@ spliceURL' maybe_mod maybe_name maybe_loc = run |
| 118 | 119 | run ('%' : '{' : 'L' : 'I' : 'N' : 'E' : '}' : rest) = line ++ run rest
|
| 119 | 120 | run (c : rest) = c : run rest
|
| 120 | 121 | |
| 121 | -renderToString :: Bool -> Html -> String
|
|
| 122 | -renderToString debug html
|
|
| 122 | +renderToBuilder :: Bool -> Html -> Builder
|
|
| 123 | +renderToBuilder debug html
|
|
| 123 | 124 | | debug = renderHtml html
|
| 124 | 125 | | otherwise = showHtml html
|
| 125 | 126 | |
| ... | ... | @@ -136,7 +137,7 @@ infixr 8 <+> |
| 136 | 137 | (<+>) :: Html -> Html -> Html
|
| 137 | 138 | a <+> b = a +++ sep +++ b
|
| 138 | 139 | where
|
| 139 | - sep = if isNoHtml a || isNoHtml b then noHtml else toHtml " "
|
|
| 140 | + sep = if isNoHtml a || isNoHtml b then noHtml else toHtml (" " :: LText)
|
|
| 140 | 141 | |
| 141 | 142 | -- | Join two 'Html' values together with a linebreak in between.
|
| 142 | 143 | -- Has 'noHtml' as left identity.
|
| ... | ... | @@ -167,7 +168,7 @@ promoQuote h = char '\'' +++ h |
| 167 | 168 | parens, brackets, pabrackets, braces :: Html -> Html
|
| 168 | 169 | parens h = char '(' +++ h +++ char ')'
|
| 169 | 170 | brackets h = char '[' +++ h +++ char ']'
|
| 170 | -pabrackets h = toHtml "[:" +++ h +++ toHtml ":]"
|
|
| 171 | +pabrackets h = toHtml ("[:" :: LText) +++ h +++ toHtml (":]" :: LText)
|
|
| 171 | 172 | braces h = char '{' +++ h +++ char '}'
|
| 172 | 173 | |
| 173 | 174 | punctuate :: Html -> [Html] -> [Html]
|
| ... | ... | @@ -188,37 +189,37 @@ ubxParenList :: [Html] -> Html |
| 188 | 189 | ubxParenList = ubxparens . hsep . punctuate comma
|
| 189 | 190 | |
| 190 | 191 | ubxSumList :: [Html] -> Html
|
| 191 | -ubxSumList = ubxparens . hsep . punctuate (toHtml " | ")
|
|
| 192 | +ubxSumList = ubxparens . hsep . punctuate (toHtml (" | " :: LText))
|
|
| 192 | 193 | |
| 193 | 194 | ubxparens :: Html -> Html
|
| 194 | -ubxparens h = toHtml "(#" <+> h <+> toHtml "#)"
|
|
| 195 | +ubxparens h = toHtml ("(#" :: LText) <+> h <+> toHtml ("#)" :: LText)
|
|
| 195 | 196 | |
| 196 | 197 | dcolon, arrow, lollipop, darrow, forallSymbol :: Bool -> Html
|
| 197 | -dcolon unicode = toHtml (if unicode then "∷" else "::")
|
|
| 198 | -arrow unicode = toHtml (if unicode then "→" else "->")
|
|
| 199 | -lollipop unicode = toHtml (if unicode then "⊸" else "%1 ->")
|
|
| 200 | -darrow unicode = toHtml (if unicode then "⇒" else "=>")
|
|
| 201 | -forallSymbol unicode = if unicode then toHtml "∀" else keyword "forall"
|
|
| 198 | +dcolon unicode = toHtml (if unicode then "∷" :: LText else "::")
|
|
| 199 | +arrow unicode = toHtml (if unicode then "→" :: LText else "->")
|
|
| 200 | +lollipop unicode = toHtml (if unicode then "⊸" :: LText else "%1 ->")
|
|
| 201 | +darrow unicode = toHtml (if unicode then "⇒" :: LText else "=>")
|
|
| 202 | +forallSymbol unicode = if unicode then toHtml ("∀" :: LText) else keyword "forall"
|
|
| 202 | 203 | |
| 203 | 204 | atSign :: Html
|
| 204 | -atSign = toHtml "@"
|
|
| 205 | +atSign = toHtml ("@" :: LText)
|
|
| 205 | 206 | |
| 206 | 207 | multAnnotation :: Html
|
| 207 | -multAnnotation = toHtml "%"
|
|
| 208 | +multAnnotation = toHtml ("%" :: LText)
|
|
| 208 | 209 | |
| 209 | 210 | dot :: Html
|
| 210 | -dot = toHtml "."
|
|
| 211 | +dot = toHtml ("." :: LText)
|
|
| 211 | 212 | |
| 212 | 213 | -- | Generate a named anchor
|
| 213 | -namedAnchor :: String -> Html -> Html
|
|
| 214 | +namedAnchor :: LText -> Html -> Html
|
|
| 214 | 215 | namedAnchor n = anchor ! [XHtml.identifier n]
|
| 215 | 216 | |
| 216 | -linkedAnchor :: String -> Html -> Html
|
|
| 217 | -linkedAnchor n = anchor ! [href ('#' : n)]
|
|
| 217 | +linkedAnchor :: LText -> Html -> Html
|
|
| 218 | +linkedAnchor n = anchor ! [href ("#" <> n)]
|
|
| 218 | 219 | |
| 219 | 220 | -- | generate an anchor identifier for a group
|
| 220 | -groupId :: String -> String
|
|
| 221 | -groupId g = makeAnchorId ("g:" ++ g)
|
|
| 221 | +groupId :: LText -> LText
|
|
| 222 | +groupId g = makeAnchorId ("g:" <> g)
|
|
| 222 | 223 | |
| 223 | 224 | --
|
| 224 | 225 | -- A section of HTML which is collapsible.
|
| ... | ... | @@ -226,7 +227,7 @@ groupId g = makeAnchorId ("g:" ++ g) |
| 226 | 227 | |
| 227 | 228 | data DetailsState = DetailsOpen | DetailsClosed
|
| 228 | 229 | |
| 229 | -collapseDetails :: String -> DetailsState -> Html -> Html
|
|
| 230 | +collapseDetails :: LText -> DetailsState -> Html -> Html
|
|
| 230 | 231 | collapseDetails id_ state = tag "details" ! (identifier id_ : openAttrs)
|
| 231 | 232 | where
|
| 232 | 233 | openAttrs = case state of DetailsOpen -> [emptyAttr "open"]; DetailsClosed -> []
|
| ... | ... | @@ -235,14 +236,14 @@ thesummary :: Html -> Html |
| 235 | 236 | thesummary = tag "summary"
|
| 236 | 237 | |
| 237 | 238 | -- | Attributes for an area that toggles a collapsed area
|
| 238 | -collapseToggle :: String -> String -> [HtmlAttr]
|
|
| 239 | +collapseToggle :: LText -> LText -> [HtmlAttr]
|
|
| 239 | 240 | collapseToggle id_ classes = [theclass cs, strAttr "data-details-id" id_]
|
| 240 | 241 | where
|
| 241 | - cs = unwords (words classes ++ ["details-toggle"])
|
|
| 242 | + cs = LText.unwords (LText.words classes <> ["details-toggle"])
|
|
| 242 | 243 | |
| 243 | 244 | -- | Attributes for an area that toggles a collapsed area,
|
| 244 | 245 | -- and displays a control.
|
| 245 | -collapseControl :: String -> String -> [HtmlAttr]
|
|
| 246 | +collapseControl :: LText -> LText -> [HtmlAttr]
|
|
| 246 | 247 | collapseControl id_ classes = collapseToggle id_ cs
|
| 247 | 248 | where
|
| 248 | - cs = unwords (words classes ++ ["details-toggle-control"]) |
|
| 249 | + cs = LText.unwords (LText.words classes <> ["details-toggle-control"]) |
| ... | ... | @@ -32,7 +32,7 @@ combineDocumentation (Documentation mDoc mWarning) = |
| 32 | 32 | --
|
| 33 | 33 | docCodeBlock :: DocH mod id -> DocH mod id
|
| 34 | 34 | docCodeBlock (DocString s) =
|
| 35 | - DocString (reverse $ dropWhile (`elem` " \t") $ reverse s)
|
|
| 35 | + DocString (reverse $ dropWhile (`elem` (" \t" :: String)) $ reverse s)
|
|
| 36 | 36 | docCodeBlock (DocAppend l r) =
|
| 37 | 37 | DocAppend l (docCodeBlock r)
|
| 38 | 38 | docCodeBlock d = d |
| ... | ... | @@ -83,6 +83,8 @@ import System.IO.Unsafe (unsafePerformIO) |
| 83 | 83 | |
| 84 | 84 | import Documentation.Haddock.Doc (emptyMetaDoc)
|
| 85 | 85 | import Haddock.Types
|
| 86 | +import Data.Text.Lazy (Text)
|
|
| 87 | +import qualified Data.Text.Lazy as LText
|
|
| 86 | 88 | |
| 87 | 89 | --------------------------------------------------------------------------------
|
| 88 | 90 | |
| ... | ... | @@ -184,35 +186,43 @@ subIndexHtmlFile ls = "doc-index-" ++ b ++ ".html" |
| 184 | 186 | -- before being matched with IDs in the target document.
|
| 185 | 187 | -------------------------------------------------------------------------------
|
| 186 | 188 | |
| 187 | -moduleUrl :: Module -> String
|
|
| 188 | -moduleUrl = moduleHtmlFile
|
|
| 189 | +moduleUrl :: Module -> Text
|
|
| 190 | +moduleUrl module_ = LText.pack (moduleHtmlFile module_)
|
|
| 189 | 191 | |
| 190 | -moduleNameUrl :: Module -> OccName -> String
|
|
| 191 | -moduleNameUrl mdl n = moduleUrl mdl ++ '#' : nameAnchorId n
|
|
| 192 | +moduleNameUrl :: Module -> OccName -> Text
|
|
| 193 | +moduleNameUrl mdl n = moduleUrl mdl <> "#" <> nameAnchorId n
|
|
| 192 | 194 | |
| 193 | -moduleNameUrl' :: ModuleName -> OccName -> String
|
|
| 194 | -moduleNameUrl' mdl n = moduleHtmlFile' mdl ++ '#' : nameAnchorId n
|
|
| 195 | +moduleNameUrl' :: ModuleName -> OccName -> Text
|
|
| 196 | +moduleNameUrl' mdl n = LText.pack (moduleHtmlFile' mdl) <> "#" <> nameAnchorId n
|
|
| 195 | 197 | |
| 196 | -nameAnchorId :: OccName -> String
|
|
| 197 | -nameAnchorId name = makeAnchorId (prefix : ':' : occNameString name)
|
|
| 198 | +nameAnchorId :: OccName -> Text
|
|
| 199 | +nameAnchorId name = makeAnchorId (prefix <> ":" <> LText.pack (occNameString name))
|
|
| 198 | 200 | where
|
| 199 | 201 | prefix
|
| 200 | - | isValOcc name = 'v'
|
|
| 201 | - | otherwise = 't'
|
|
| 202 | + | isValOcc name = "v"
|
|
| 203 | + | otherwise = "t"
|
|
| 202 | 204 | |
| 203 | 205 | -- | Takes an arbitrary string and makes it a valid anchor ID. The mapping is
|
| 204 | 206 | -- identity preserving.
|
| 205 | -makeAnchorId :: String -> String
|
|
| 206 | -makeAnchorId [] = []
|
|
| 207 | -makeAnchorId (f : r) = escape isAlpha f ++ concatMap (escape isLegal) r
|
|
| 207 | +makeAnchorId :: Text -> Text
|
|
| 208 | +makeAnchorId input =
|
|
| 209 | + case LText.uncons input of
|
|
| 210 | + Nothing -> LText.empty
|
|
| 211 | + Just (f, rest) ->
|
|
| 212 | + escape isAlpha f <> LText.concatMap (escape isLegal) rest
|
|
| 208 | 213 | where
|
| 214 | + escape :: (Char -> Bool) -> Char -> Text
|
|
| 209 | 215 | escape p c
|
| 210 | - | p c = [c]
|
|
| 211 | - | otherwise = '-' : show (ord c) ++ "-"
|
|
| 216 | + | p c = LText.singleton c
|
|
| 217 | + | otherwise =
|
|
| 218 | + -- "-" <> show (ord c) <> "-"
|
|
| 219 | + LText.cons '-' (LText.pack (show (ord c) <> "-"))
|
|
| 220 | + |
|
| 221 | + isLegal :: Char -> Bool
|
|
| 212 | 222 | isLegal ':' = True
|
| 213 | 223 | isLegal '_' = True
|
| 214 | 224 | isLegal '.' = True
|
| 215 | - isLegal c = isAscii c && isAlphaNum c
|
|
| 225 | + isLegal c = isAscii c && isAlphaNum c
|
|
| 216 | 226 | |
| 217 | 227 | -- NB: '-' is legal in IDs, but we use it as the escape char
|
| 218 | 228 | |
| ... | ... | @@ -272,7 +282,7 @@ escapeURIString :: (Char -> Bool) -> String -> String |
| 272 | 282 | escapeURIString = concatMap . escapeURIChar
|
| 273 | 283 | |
| 274 | 284 | isUnreserved :: Char -> Bool
|
| 275 | -isUnreserved c = isAlphaNumChar c || (c `elem` "-_.~")
|
|
| 285 | +isUnreserved c = isAlphaNumChar c || (c `elem` ("-_.~" :: String))
|
|
| 276 | 286 | |
| 277 | 287 | isAlphaChar, isDigitChar, isAlphaNumChar :: Char -> Bool
|
| 278 | 288 | isAlphaChar c = (c >= 'A' && c <= 'Z') || (c >= 'a' && c <= 'z')
|
| ... | ... | @@ -53,7 +53,7 @@ |
| 53 | 53 | >Description</p
|
| 54 | 54 | ><div class="doc"
|
| 55 | 55 | ><p
|
| 56 | - >This module tests the ‘@since …’ annotation.</p
|
|
| 56 | + >This module tests the ‘@since …’ annotation.</p
|
|
| 57 | 57 | ><p
|
| 58 | 58 | ><em
|
| 59 | 59 | >Since: 1.2.3</em
|
| ... | ... | @@ -67,7 +67,7 @@ |
| 67 | 67 | > :: a -> a -> a</li
|
| 68 | 68 | ><li class="src short"
|
| 69 | 69 | ><a href="#"
|
| 70 | - >(⋆^)</a
|
|
| 70 | + >(⋆^)</a
|
|
| 71 | 71 | > :: a -> a -> a</li
|
| 72 | 72 | ><li class="src short"
|
| 73 | 73 | ><a href="#"
|
| ... | ... | @@ -106,7 +106,7 @@ |
| 106 | 106 | ><div class="top"
|
| 107 | 107 | ><p class="src"
|
| 108 | 108 | ><a id="v:-8902--94-" class="def"
|
| 109 | - >(⋆^)</a
|
|
| 109 | + >(⋆^)</a
|
|
| 110 | 110 | > :: a -> a -> a <a href="#" class="selflink"
|
| 111 | 111 | >#</a
|
| 112 | 112 | ></p
|
| ... | ... | @@ -134,7 +134,7 @@ |
| 134 | 134 | ></code
|
| 135 | 135 | > and <code
|
| 136 | 136 | ><a href="#" title="Bug298"
|
| 137 | - >⋆^</a
|
|
| 137 | + >⋆^</a
|
|
| 138 | 138 | ></code
|
| 139 | 139 | >.</p
|
| 140 | 140 | ></div
|
| ... | ... | @@ -55,7 +55,7 @@ |
| 55 | 55 | ><ul class="details-toggle" data-details-id="syn"
|
| 56 | 56 | ><li class="src short"
|
| 57 | 57 | ><a href="#"
|
| 58 | - >(⊆)</a
|
|
| 58 | + >(⊆)</a
|
|
| 59 | 59 | > :: () -> () -> ()</li
|
| 60 | 60 | ></ul
|
| 61 | 61 | ></details
|
| ... | ... | @@ -66,7 +66,7 @@ |
| 66 | 66 | ><div class="top"
|
| 67 | 67 | ><p class="src"
|
| 68 | 68 | ><a id="v:-8838-" class="def"
|
| 69 | - >(⊆)</a
|
|
| 69 | + >(⊆)</a
|
|
| 70 | 70 | > :: () -> () -> () <a href="#" class="selflink"
|
| 71 | 71 | >#</a
|
| 72 | 72 | ></p
|
| ... | ... | @@ -75,7 +75,7 @@ |
| 75 | 75 | >See the defn of <code class="inline-code"
|
| 76 | 76 | ><code
|
| 77 | 77 | ><a href="#" title="Bug458"
|
| 78 | - >⊆</a
|
|
| 78 | + >⊆</a
|
|
| 79 | 79 | ></code
|
| 80 | 80 | ></code
|
| 81 | 81 | >.</p
|
| ... | ... | @@ -317,7 +317,7 @@ with more of the indented list content.</p |
| 317 | 317 | ><h3
|
| 318 | 318 | >Level 3 header</h3
|
| 319 | 319 | ><p
|
| 320 | - >with some content…</p
|
|
| 320 | + >with some content…</p
|
|
| 321 | 321 | ><ul
|
| 322 | 322 | ><li
|
| 323 | 323 | >and even more lists inside</li
|
| ... | ... | @@ -105,7 +105,7 @@ |
| 105 | 105 | ><a href="#" title="TitledPicture"
|
| 106 | 106 | >bar</a
|
| 107 | 107 | ></code
|
| 108 | - > with title <img src="un∣∁∘" title="δ∈"
|
|
| 108 | + > with title <img src="un∣∁∘" title="δ∈"
|
|
| 109 | 109 | /></p
|
| 110 | 110 | ></div
|
| 111 | 111 | ></div
|
| ... | ... | @@ -76,7 +76,7 @@ |
| 76 | 76 | ></p
|
| 77 | 77 | ><div class="doc"
|
| 78 | 78 | ><p
|
| 79 | - >γλώσσα</p
|
|
| 79 | + >γλώσσα</p
|
|
| 80 | 80 | ></div
|
| 81 | 81 | ></div
|
| 82 | 82 | ></div
|
| ... | ... | @@ -55,7 +55,7 @@ |
| 55 | 55 | ><ul class="details-toggle" data-details-id="syn"
|
| 56 | 56 | ><li class="src short"
|
| 57 | 57 | ><a href="#"
|
| 58 | - >ü</a
|
|
| 58 | + >ü</a
|
|
| 59 | 59 | > :: ()</li
|
| 60 | 60 | ></ul
|
| 61 | 61 | ></details
|
| ... | ... | @@ -66,36 +66,36 @@ |
| 66 | 66 | ><div class="top"
|
| 67 | 67 | ><p class="src"
|
| 68 | 68 | ><a id="v:-252-" class="def"
|
| 69 | - >ü</a
|
|
| 69 | + >ü</a
|
|
| 70 | 70 | > :: () <a href="#" class="selflink"
|
| 71 | 71 | >#</a
|
| 72 | 72 | ></p
|
| 73 | 73 | ><div class="doc"
|
| 74 | 74 | ><p
|
| 75 | - >All of the following work with a unicode character ü:</p
|
|
| 75 | + >All of the following work with a unicode character ü:</p
|
|
| 76 | 76 | ><ul
|
| 77 | 77 | ><li
|
| 78 | 78 | >an italicized <em
|
| 79 | - >ü</em
|
|
| 79 | + >ü</em
|
|
| 80 | 80 | ></li
|
| 81 | 81 | ><li
|
| 82 | 82 | >inline code <code class="inline-code"
|
| 83 | - >ü</code
|
|
| 83 | + >ü</code
|
|
| 84 | 84 | ></li
|
| 85 | 85 | ><li
|
| 86 | 86 | >a code block:</li
|
| 87 | 87 | ></ul
|
| 88 | 88 | ><pre
|
| 89 | - >ü</pre
|
|
| 89 | + >ü</pre
|
|
| 90 | 90 | ><ul
|
| 91 | 91 | ><li
|
| 92 | 92 | >a url <a href="#"
|
| 93 | - >https://www.google.com/search?q=ü</a
|
|
| 93 | + >https://www.google.com/search?q=ü</a
|
|
| 94 | 94 | ></li
|
| 95 | 95 | ><li
|
| 96 | 96 | >a link to <code
|
| 97 | 97 | ><a href="#" title="Unicode2"
|
| 98 | - >ü</a
|
|
| 98 | + >ü</a
|
|
| 99 | 99 | ></code
|
| 100 | 100 | ></li
|
| 101 | 101 | ></ul
|