def test_example_BSSN():
     import NRPy_param_funcs as par, reference_metric as rfm, BSSN.BSSN_RHSs as Brhs
     Parser.clear_namespace()
     parse(r"""
         % define deltaDD (3D), sym01 hDD (3D), sym01 aDD (3D), vetU (3D)
         % parse \hat{\gamma}_{ij} = \delta_{ij}
         % assign symbolic <H> gammahatDD
         % parse \bar{\gamma}_{ij} = h_{ij} + \hat{\gamma}_{ij}
         % assign numeric hDD, aDD, vetU, gammabarDD
         % assign metric gammahatDD, gammabarDD
         % srepl "\bar{A}" -> "a", "\beta" -> "\text{vet}"
         % parse \bar{A}^i_j = \bar{\gamma}^{ik} \bar{A}_{kj}
         \begin{align}
             % define basis [x, y, z]
             %% parse \partial_k \bar{\gamma}_{ij} = \vphantom{upwind} \partial_k h_{ij} + \partial_k \hat{\gamma}_{ij}
             % srepl "\text{vet}^<1> \partial_<1>" -> "\text{vet}^<1> \vphantom{upwind} \partial_<1>" %% (inside Lie derivative expansion)
             % srepl "\bar{D}_k \text{vet}^k" -> "(\partial_k \text{vet}^k + \frac{\text{vet}^k \vphantom{symbolic} \partial_k \text{gammabardet}}{2 \text{gammabardet}})"
             % srepl "\partial_t \bar{\gamma}" -> "\text{h_rhs}"
             \partial_t \bar{\gamma}_{ij} &= \mathcal{L}_\beta \bar{\gamma}_{ij}
                 + \frac{2}{3} \bar{\gamma}_{ij} \left(\alpha \bar{A}^k{}_k - \bar{D}_k \beta^k\right) - 2 \alpha \bar{A}_{ij}
             % srepl "K" -> "\text{trK}", "\phi" -> "\text{cf}", "\partial_t \text{cf}" -> "\text{cf_rhs}"
             \partial_t \phi &= \mathcal{L}_\beta \phi - \frac{1}{3} \phi \left(\bar{D}_k \beta^k - \alpha K \right)
         \end{align}
     """)
     par.set_parval_from_str('reference_metric::CoordSystem', 'Cartesian')
     rfm.reference_metric()
     Brhs.BSSN_RHSs()
     assert_equal({
         'h_rhsDD': h_rhsDD,
         'cf_rhs': cf_rhs
     }, {
         'h_rhsDD': Brhs.h_rhsDD,
         'cf_rhs': Brhs.cf_rhs
     })
Пример #2
0
    def Ricci__generate_symbolic_expressions():
        ######################################
        # START: GENERATE SYMBOLIC EXPRESSIONS
        print("Generating symbolic expressions for Ricci tensor...")
        start = time.time()
        # Enable rfm_precompute infrastructure, which results in
        #   BSSN RHSs that are free of transcendental functions,
        #   even in curvilinear coordinates, so long as
        #   ConformalFactor is set to "W" (default).
        par.set_parval_from_str("reference_metric::enable_rfm_precompute","True")
        par.set_parval_from_str("reference_metric::rfm_precompute_Ccode_outdir",os.path.join(outdir,"rfm_files/"))

        # Evaluate BSSN + BSSN gauge RHSs with rfm_precompute enabled:
        import BSSN.BSSN_quantities as Bq

        # Next compute Ricci tensor
        # par.set_parval_from_str("BSSN.BSSN_quantities::LeaveRicciSymbolic","False")
        RbarDD_already_registered = False
        for i in range(len(gri.glb_gridfcs_list)):
            if "RbarDD00" in gri.glb_gridfcs_list[i].name:
                RbarDD_already_registered = True
        if not RbarDD_already_registered:
            # We ignore the return value of ixp.register_gridfunctions_for_single_rank2() below
            #    as it is unused.
            ixp.register_gridfunctions_for_single_rank2("AUXEVOL","RbarDD","sym01")
        rhs.BSSN_RHSs()
        Bq.RicciBar__gammabarDD_dHatD__DGammaUDD__DGammaU()

        # Now that we are finished with all the rfm hatted
        #           quantities in generic precomputed functional
        #           form, let's restore them to their closed-
        #           form expressions.
        par.set_parval_from_str("reference_metric::enable_rfm_precompute","False") # Reset to False to disable rfm_precompute.
        rfm.ref_metric__hatted_quantities()
        end = time.time()
        print("(BENCH) Finished Ricci symbolic expressions in "+str(end-start)+" seconds.")
        # END: GENERATE SYMBOLIC EXPRESSIONS
        ######################################

        Ricci_SymbExpressions = [lhrh(lhs=gri.gfaccess("auxevol_gfs","RbarDD00"),rhs=Bq.RbarDD[0][0]),
                                 lhrh(lhs=gri.gfaccess("auxevol_gfs","RbarDD01"),rhs=Bq.RbarDD[0][1]),
                                 lhrh(lhs=gri.gfaccess("auxevol_gfs","RbarDD02"),rhs=Bq.RbarDD[0][2]),
                                 lhrh(lhs=gri.gfaccess("auxevol_gfs","RbarDD11"),rhs=Bq.RbarDD[1][1]),
                                 lhrh(lhs=gri.gfaccess("auxevol_gfs","RbarDD12"),rhs=Bq.RbarDD[1][2]),
                                 lhrh(lhs=gri.gfaccess("auxevol_gfs","RbarDD22"),rhs=Bq.RbarDD[2][2])]

        return [Ricci_SymbExpressions]
Пример #3
0
    def BSSN_RHSs__generate_symbolic_expressions():
        ######################################
        # START: GENERATE SYMBOLIC EXPRESSIONS
        print("Generating symbolic expressions for BSSN RHSs...")
        start = time.time()
        # Enable rfm_precompute infrastructure, which results in
        #   BSSN RHSs that are free of transcendental functions,
        #   even in curvilinear coordinates, so long as
        #   ConformalFactor is set to "W" (default).
        par.set_parval_from_str("reference_metric::enable_rfm_precompute","True")
        par.set_parval_from_str("reference_metric::rfm_precompute_Ccode_outdir",os.path.join(outdir,"rfm_files/"))

        # Evaluate BSSN + BSSN gauge RHSs with rfm_precompute enabled:
        import BSSN.BSSN_quantities as Bq
        par.set_parval_from_str("BSSN.BSSN_quantities::LeaveRicciSymbolic","True")

        rhs.BSSN_RHSs()

        if T4UU != None:
            import BSSN.BSSN_stress_energy_source_terms as Bsest
            Bsest.BSSN_source_terms_for_BSSN_RHSs(T4UU)
            rhs.trK_rhs += Bsest.sourceterm_trK_rhs
            for i in range(3):
                # Needed for Gamma-driving shift RHSs:
                rhs.Lambdabar_rhsU[i] += Bsest.sourceterm_Lambdabar_rhsU[i]
                # Needed for BSSN RHSs:
                rhs.lambda_rhsU[i]    += Bsest.sourceterm_lambda_rhsU[i]
                for j in range(3):
                    rhs.a_rhsDD[i][j] += Bsest.sourceterm_a_rhsDD[i][j]

        gaugerhs.BSSN_gauge_RHSs()

        # Add Kreiss-Oliger dissipation to the BSSN RHSs:
        thismodule = "KO_Dissipation"
        diss_strength = par.Cparameters("REAL", thismodule, "diss_strength", default_KO_strength)

        alpha_dKOD = ixp.declarerank1("alpha_dKOD")
        cf_dKOD    = ixp.declarerank1("cf_dKOD")
        trK_dKOD   = ixp.declarerank1("trK_dKOD")
        betU_dKOD    = ixp.declarerank2("betU_dKOD","nosym")
        vetU_dKOD    = ixp.declarerank2("vetU_dKOD","nosym")
        lambdaU_dKOD = ixp.declarerank2("lambdaU_dKOD","nosym")
        aDD_dKOD = ixp.declarerank3("aDD_dKOD","sym01")
        hDD_dKOD = ixp.declarerank3("hDD_dKOD","sym01")
        for k in range(3):
            gaugerhs.alpha_rhs += diss_strength*alpha_dKOD[k]*rfm.ReU[k] # ReU[k] = 1/scalefactor_orthog_funcform[k]
            rhs.cf_rhs         += diss_strength*   cf_dKOD[k]*rfm.ReU[k] # ReU[k] = 1/scalefactor_orthog_funcform[k]
            rhs.trK_rhs        += diss_strength*  trK_dKOD[k]*rfm.ReU[k] # ReU[k] = 1/scalefactor_orthog_funcform[k]
            for i in range(3):
                if "2ndOrder" in ShiftCondition:
                    gaugerhs.bet_rhsU[i] += diss_strength*   betU_dKOD[i][k]*rfm.ReU[k] # ReU[k] = 1/scalefactor_orthog_funcform[k]
                gaugerhs.vet_rhsU[i]     += diss_strength*   vetU_dKOD[i][k]*rfm.ReU[k] # ReU[k] = 1/scalefactor_orthog_funcform[k]
                rhs.lambda_rhsU[i]       += diss_strength*lambdaU_dKOD[i][k]*rfm.ReU[k] # ReU[k] = 1/scalefactor_orthog_funcform[k]
                for j in range(3):
                    rhs.a_rhsDD[i][j] += diss_strength*aDD_dKOD[i][j][k]*rfm.ReU[k] # ReU[k] = 1/scalefactor_orthog_funcform[k]
                    rhs.h_rhsDD[i][j] += diss_strength*hDD_dKOD[i][j][k]*rfm.ReU[k] # ReU[k] = 1/scalefactor_orthog_funcform[k]

        # We use betaU as our upwinding control vector:
        Bq.BSSN_basic_tensors()
        betaU = Bq.betaU

        # Now that we are finished with all the rfm hatted
        #           quantities in generic precomputed functional
        #           form, let's restore them to their closed-
        #           form expressions.
        par.set_parval_from_str("reference_metric::enable_rfm_precompute","False") # Reset to False to disable rfm_precompute.
        rfm.ref_metric__hatted_quantities()
        par.set_parval_from_str("BSSN.BSSN_quantities::LeaveRicciSymbolic","False")
        end = time.time()
        print("(BENCH) Finished BSSN RHS symbolic expressions in "+str(end-start)+" seconds.")
        # END: GENERATE SYMBOLIC EXPRESSIONS
        ######################################

        BSSN_RHSs_SymbExpressions = [lhrh(lhs=gri.gfaccess("rhs_gfs","aDD00"),   rhs=rhs.a_rhsDD[0][0]),
                                     lhrh(lhs=gri.gfaccess("rhs_gfs","aDD01"),   rhs=rhs.a_rhsDD[0][1]),
                                     lhrh(lhs=gri.gfaccess("rhs_gfs","aDD02"),   rhs=rhs.a_rhsDD[0][2]),
                                     lhrh(lhs=gri.gfaccess("rhs_gfs","aDD11"),   rhs=rhs.a_rhsDD[1][1]),
                                     lhrh(lhs=gri.gfaccess("rhs_gfs","aDD12"),   rhs=rhs.a_rhsDD[1][2]),
                                     lhrh(lhs=gri.gfaccess("rhs_gfs","aDD22"),   rhs=rhs.a_rhsDD[2][2]),
                                     lhrh(lhs=gri.gfaccess("rhs_gfs","alpha"),   rhs=gaugerhs.alpha_rhs),
                                     lhrh(lhs=gri.gfaccess("rhs_gfs","betU0"),   rhs=gaugerhs.bet_rhsU[0]),
                                     lhrh(lhs=gri.gfaccess("rhs_gfs","betU1"),   rhs=gaugerhs.bet_rhsU[1]),
                                     lhrh(lhs=gri.gfaccess("rhs_gfs","betU2"),   rhs=gaugerhs.bet_rhsU[2]),
                                     lhrh(lhs=gri.gfaccess("rhs_gfs","cf"),      rhs=rhs.cf_rhs),
                                     lhrh(lhs=gri.gfaccess("rhs_gfs","hDD00"),   rhs=rhs.h_rhsDD[0][0]),
                                     lhrh(lhs=gri.gfaccess("rhs_gfs","hDD01")   ,rhs=rhs.h_rhsDD[0][1]),
                                     lhrh(lhs=gri.gfaccess("rhs_gfs","hDD02"),   rhs=rhs.h_rhsDD[0][2]),
                                     lhrh(lhs=gri.gfaccess("rhs_gfs","hDD11"),   rhs=rhs.h_rhsDD[1][1]),
                                     lhrh(lhs=gri.gfaccess("rhs_gfs","hDD12"),   rhs=rhs.h_rhsDD[1][2]),
                                     lhrh(lhs=gri.gfaccess("rhs_gfs","hDD22"),   rhs=rhs.h_rhsDD[2][2]),
                                     lhrh(lhs=gri.gfaccess("rhs_gfs","lambdaU0"),rhs=rhs.lambda_rhsU[0]),
                                     lhrh(lhs=gri.gfaccess("rhs_gfs","lambdaU1"),rhs=rhs.lambda_rhsU[1]),
                                     lhrh(lhs=gri.gfaccess("rhs_gfs","lambdaU2"),rhs=rhs.lambda_rhsU[2]),
                                     lhrh(lhs=gri.gfaccess("rhs_gfs","trK"),     rhs=rhs.trK_rhs),
                                     lhrh(lhs=gri.gfaccess("rhs_gfs","vetU0"),   rhs=gaugerhs.vet_rhsU[0]),
                                     lhrh(lhs=gri.gfaccess("rhs_gfs","vetU1"),   rhs=gaugerhs.vet_rhsU[1]),
                                     lhrh(lhs=gri.gfaccess("rhs_gfs","vetU2"),   rhs=gaugerhs.vet_rhsU[2]) ]

        return [betaU,BSSN_RHSs_SymbExpressions]
    def test_example_BSSN():
        parse_latex(r"""
            \begin{align}
                % keydef basis [x, y, z]
                % ignore "\\%", "\qquad"

                % vardef -kron 'deltaDD'
                % parse \hat{\gamma}_{ij} = \delta_{ij}
                % assign -diff_type=symbolic -metric 'gammahatDD'
                % vardef -diff_type=dD -symmetry=sym01 'hDD'
                % parse \bar{\gamma}_{ij} = h_{ij} + \hat{\gamma}_{ij}
                % assign -diff_type=dD -metric 'gammabarDD'

                % srepl "\beta" -> "\text{vet}"
                % vardef -diff_type=dD 'vetU'
                %% upwind pattern inside Lie derivative expansion
                % srepl -persist "\text{vet}^{<1>} \partial_{<1>}" -> "\text{vet}^{<1>} \vphantom{dupD} \partial_{<1>}"
                %% substitute tensor identity (see appropriate BSSN notebook)
                % srepl "\bar{D}_k \text{vet}^k" -> "(\partial_k \text{vet}^k + \frac{\partial_k \text{gammahatdet} \text{vet}^k}{2 \text{gammahatdet}})"

                % srepl "\bar{A}" -> "\text{a}"
                % vardef -diff_type=dD -symmetry=sym01 'aDD'
                % assign -metric='gammabar' 'aDD'
                % srepl "\partial_t \bar{\gamma}" -> "\text{h_rhs}"
                \partial_t \bar{\gamma}_{ij} &= \mathcal{L}_\beta \bar{\gamma}_{ij}
                    + \frac{2}{3} \bar{\gamma}_{ij} \left(\alpha \bar{A}^k{}_k - \bar{D}_k \beta^k\right) - 2 \alpha \bar{A}_{ij} \\

                % srepl "K" -> "\text{trK}"
                % vardef -diff_type=dD 'cf', 'trK'
                %% replace 'phi' with conformal factor cf = W = e^{-2\phi}
                % srepl "e^{-4\phi}" -> "\text{cf}^2"
                % srepl "\partial_t \phi = <1..> \\" -> "\text{cf_rhs} = -2 \text{cf} (<1..>) \\"
                % srepl -persist "\partial_{<1>} \phi" -> "\partial_{<1>} \text{cf} \frac{-1}{2 \text{cf}}"
                % srepl "\partial_<1> \phi" -> "\partial_<1> \text{cf} \frac{-1}{2 \text{cf}}"
                \partial_t \phi &= \mathcal{L}_\beta \phi + \frac{1}{6} \left(\bar{D}_k \beta^k - \alpha K \right) \\

                % vardef -diff_type=dD 'alpha'
                % srepl "\partial_t \text{trK}" -> "\text{trK_rhs}"
                \partial_t K &= \mathcal{L}_\beta K + \frac{1}{3} \alpha K^2 + \alpha \bar{A}_{ij} \bar{A}^{ij}
                    - e^{-4\phi} \left(\bar{D}_i \bar{D}^i \alpha + 2 \bar{D}^i \alpha \bar{D}_i \phi\right) \\

                % srepl "\bar{\Lambda}" -> "\text{lambda}"
                % vardef -diff_type=dD 'lambdaU'
                % parse \Delta^k_{ij} = \bar{\Gamma}^k_{ij} - \hat{\Gamma}^k_{ij}
                % assign -metric='gammabar' 'DeltaUDD'
                % parse \Delta^k = \bar{\gamma}^{ij} \Delta^k_{ij}
                % srepl "\partial_t \text{lambda}" -> "\text{Lambdabar_rhs}"
                \partial_t \bar{\Lambda}^i &= \mathcal{L}_\beta \bar{\Lambda}^i + \bar{\gamma}^{jk} \hat{D}_j \hat{D}_k \beta^i
                    + \frac{2}{3} \Delta^i \bar{D}_k \beta^k + \frac{1}{3} \bar{D}^i \bar{D}_k \beta^k \\%
                    &\qquad- 2 \bar{A}^{ij} \left(\partial_j \alpha - 6 \alpha \partial_j \phi\right)
                    + 2 \alpha \bar{A}^{jk} \Delta^i_{jk} - \frac{4}{3} \alpha \bar{\gamma}^{ij} \partial_j K \\

                % vardef -diff_type=dD -symmetry=sym01 'RbarDD'
                X_{ij} &= -2 \alpha \bar{D}_i \bar{D}_j \phi + 4 \alpha \bar{D}_i \phi \bar{D}_j \phi
                    + 2 \bar{D}_i \alpha \bar{D}_j \phi + 2 \bar{D}_j \alpha \bar{D}_i \phi
                    - \bar{D}_i \bar{D}_j \alpha + \alpha \bar{R}_{ij} \\
                \hat{X}_{ij} &= X_{ij} - \frac{1}{3} \bar{\gamma}_{ij} \bar{\gamma}^{kl} X_{kl} \\
                % srepl "\partial_t \text{a}" -> "\text{a_rhs}"
                \partial_t \bar{A}_{ij} &= \mathcal{L}_\beta \bar{A}_{ij} - \frac{2}{3} \bar{A}_{ij} \bar{D}_k \beta^k
                    - 2 \alpha \bar{A}_{ik} \bar{A}^k_j + \alpha \bar{A}_{ij} K + e^{-4\phi} \hat{X}_{ij} \\

                % srepl "\partial_t \alpha" -> "\text{alpha_rhs}"
                \partial_t \alpha &= \mathcal{L}_\beta \alpha - 2 \alpha K \\

                % srepl "B" -> "\text{bet}"
                % vardef -diff_type=dD 'betU'
                % srepl "\partial_t \text{vet}" -> "\text{vet_rhs}"
                \partial_t \beta^i &= \left[\beta^j \vphantom{dupD} \bar{D}_j \beta^i\right] + B^i \\

                % vardef -const 'eta'
                % srepl "\partial_t \text{bet}" -> "\text{bet_rhs}"
                \partial_t B^i &= \left[\beta^j \vphantom{dupD} \bar{D}_j B^i\right]
                    + \frac{3}{4} \left(\partial_t \bar{\Lambda}^i - \left[\beta^j \vphantom{dupD} \bar{D}_j \bar{\Lambda}^i\right]\right) - \eta B^i \\

                % parse \bar{R} = \bar{\gamma}^{ij} \bar{R}_{ij}
                % srepl "\bar{D}^2" -> "\bar{D}^i \bar{D}_i", "\mathcal{<1>}" -> "<1>"
                \mathcal{H} &= \frac{2}{3} K^2 - \bar{A}_{ij} \bar{A}^{ij}
                    + e^{-4\phi} \left(\bar{R} - 8 \bar{D}^i \phi \bar{D}_i \phi - 8 \bar{D}^2 \phi\right) \\

                \mathcal{M}^i &= e^{-4\phi} \left(\bar{D}_j \bar{A}^{ij} + 6 \bar{A}^{ij} \partial_j \phi
                    - \frac{2}{3} \bar{\gamma}^{ij} \partial_j K\right) \\

                \bar{R}_{ij} &= -\frac{1}{2} \bar{\gamma}^{kl} \hat{D}_k \hat{D}_l \bar{\gamma}_{ij}
                    + \frac{1}{2} \left(\bar{\gamma}_{ki} \hat{D}_j \bar{\Lambda}^k + \bar{\gamma}_{kj} \hat{D}_i \bar{\Lambda}^k\right)
                    + \frac{1}{2} \Delta^k \left(\Delta_{ijk} + \Delta_{jik}\right) \\%
                    &\qquad+ \bar{\gamma}^{kl} \left(\Delta^m_{ki} \Delta_{jml} + \Delta^m_{kj} \Delta_{iml} + \Delta^m_{ik} \Delta_{mjl}\right)
            \end{align}
        """,
                    ignore_warning=True)
        par.set_parval_from_str('reference_metric::CoordSystem', 'Cartesian')
        par.set_parval_from_str('BSSN.BSSN_quantities::LeaveRicciSymbolic',
                                'True')
        rfm.reference_metric()
        Brhs.BSSN_RHSs()
        gaugerhs.BSSN_gauge_RHSs()
        bssncon.BSSN_constraints()
        par.set_parval_from_str('BSSN.BSSN_quantities::LeaveRicciSymbolic',
                                'False')
        Bq.RicciBar__gammabarDD_dHatD__DGammaUDD__DGammaU()
        assert_equal(
            {
                'h_rhsDD': h_rhsDD,
                'cf_rhs': cf_rhs,
                'trK_rhs': trK_rhs,
                'Lambdabar_rhsU': Lambdabar_rhsU,
                'a_rhsDD': a_rhsDD,
                'alpha_rhs': alpha_rhs,
                'vet_rhsU': vet_rhsU,
                'bet_rhsU': bet_rhsU,
                'H': H,
                'MU': MU,
                'RbarDD': RbarDD
            }, {
                'h_rhsDD': Brhs.h_rhsDD,
                'cf_rhs': Brhs.cf_rhs,
                'trK_rhs': Brhs.trK_rhs,
                'Lambdabar_rhsU': Brhs.Lambdabar_rhsU,
                'a_rhsDD': Brhs.a_rhsDD,
                'alpha_rhs': gaugerhs.alpha_rhs,
                'vet_rhsU': gaugerhs.vet_rhsU,
                'bet_rhsU': gaugerhs.bet_rhsU,
                'H': bssncon.H,
                'MU': bssncon.MU,
                'RbarDD': Bq.RbarDD
            },
            suppress_message=True)
Пример #5
0
    def test_example_BSSN():
        import NRPy_param_funcs as par, reference_metric as rfm
        import BSSN.BSSN_RHSs as Brhs, BSSN.BSSN_quantities as Bq
        Parser.clear_namespace()
        parse(r"""
            % keydef basis [x, y, z]
            % ignore "\\%", "\qquad"
            % vardef 'deltaDD', 'vetU', 'lambdaU'
            % vardef -numeric -sym01 'hDD', 'aDD', 'RbarDD'
            % assign -numeric 'cf', 'alpha', 'trK', 'vetU', 'lambdaU'
            % parse \hat{\gamma}_{ij} = \delta_{ij}
            % assign -symbolic <H> -metric 'gammahatDD'
            % parse \bar{\gamma}_{ij} = h_{ij} + \hat{\gamma}_{ij}
            % assign -numeric -metric 'gammabarDD'
            \begin{align}
                %% replace LaTeX variable(s) with BSSN variable(s)
                % srepl "\bar{A}" -> "\text{a}", "\beta" -> "\text{vet}", "K" -> "\text{trK}", "\bar{\Lambda}" -> "\text{lambda}"
                % srepl "e^{{-4\phi}}" -> "\text{cf}^{{2}}"
                % srepl "\partial_t \phi = <1..> \\" -> "\text{cf_rhs} = -2 \text{cf} (<1..>) \\"
                % srepl -global "\partial_<1> \phi"         -> "\partial_<1> \text{cf} \frac{-1}{2 \text{cf}}"
                % srepl -global "\partial_<1> \text{phi}"   -> "\partial_<1> \text{cf} \frac{-1}{2 \text{cf}}"
                % srepl -global "\partial_<1> (\text{phi})" -> "\partial_<1> \text{cf} \frac{-1}{2 \text{cf}}"

                %% upwind pattern inside Lie derivative expansion
                % srepl -global "\text{vet}^<1> \partial_<1>" -> "\text{vet}^<1> \vphantom{upwind} \partial_<1>"

                %% enforce metric constraint gammabardet == gammahatdet
                % srepl -global "\bar{D}^i \bar{D}_k \text{vet}^k" -> "(\bar{D}^i \partial_k \text{vet}^k)"
                % srepl -global "\bar{D}_k \text{vet}^k" -> "(\partial_k \text{vet}^k + \frac{\partial_k \text{gammahatdet} \text{vet}^k}{2 \text{gammahatdet}})"

                % parse \bar{A}^i_j = \bar{\gamma}^{ik} \bar{A}_{kj}
                % srepl "\partial_t \bar{\gamma}" -> "\text{h_rhs}"
                \partial_t \bar{\gamma}_{ij} &= \mathcal{L}_\beta \bar{\gamma}_{ij}
                    + \frac{2}{3} \bar{\gamma}_{ij} \left(\alpha \bar{A}^k{}_k - \bar{D}_k \beta^k\right)
                    - 2 \alpha \bar{A}_{ij} \\

                \partial_t \phi &= \mathcal{L}_\beta \phi
                    + \frac{1}{6} \left(\bar{D}_k \beta^k - \alpha K \right) \\

                % parse \bar{A}^{ij} = \bar{\gamma}^{ik} \bar{\gamma}^{jl} \bar{A}_{kl}
                % srepl "\partial_t \text{trK}" -> "\text{trK_rhs}"
                \partial_t K &= \mathcal{L}_\beta K
                    + \frac{1}{3} \alpha K^{{2}}
                    + \alpha \bar{A}_{ij} \bar{A}^{ij}
                    - e^{{-4\phi}} \left(\bar{D}_i \bar{D}^i \alpha + 2 \bar{D}^i \alpha \bar{D}_i \phi\right) \\

                % parse \Pi^k_{ij} = \bar{\Gamma}^k_{ij} - \hat{\Gamma}^k_{ij}
                % parse \Pi_{ijk}  = \bar{\gamma}_{il} \Pi^l_{jk}
                % parse \Pi^k = \bar{\gamma}^{ij} \Pi^k_{ij}
                % srepl "\partial_t \text{lambda}" -> "\text{Lambdabar_rhs}"
                \partial_t \bar{\Lambda}^i &= \mathcal{L}_\beta \bar{\Lambda}^i + \bar{\gamma}^{jk} \hat{D}_j \hat{D}_k \beta^i
                    + \frac{2}{3} \Pi^i \bar{D}_k \beta^k + \frac{1}{3} \bar{D}^i \bar{D}_k \beta^k \\%
                    &\qquad- 2 \bar{A}^{ij} (\partial_j \alpha - 6 \alpha \partial_j \phi)
                    + 2 \alpha \bar{A}^{jk} \Pi^i_{jk} - \frac{4}{3} \alpha \bar{\gamma}^{ij} \partial_j K \\

                X_{ij} &= -2 \alpha \bar{D}_i \bar{D}_j \phi + 4 \alpha \bar{D}_i \phi \bar{D}_j \phi
                    + 2 \bar{D}_i \alpha \bar{D}_j \phi + 2 \bar{D}_j \alpha \bar{D}_i \phi
                    - \bar{D}_i \bar{D}_j \alpha + \alpha \bar{R}_{ij} \\
                \hat{X}_{ij} &= X_{ij} - \frac{1}{3} \bar{\gamma}_{ij} \bar{\gamma}^{kl} X_{kl} \\
                % srepl "\partial_t \text{a}" -> "\text{a_rhs}"
                \partial_t \bar{A}_{ij} &= \mathcal{L}_\beta \bar{A}_{ij}
                    - \frac{2}{3} \bar{A}_{ij} \bar{D}_k \beta^k
                    - 2 \alpha \bar{A}_{ik} \bar{A}^k_j
                    + \alpha \bar{A}_{ij} K
                    + e^{{-4\phi}} \hat{X}_{ij} \\

                \bar{R}_{ij} &= -\frac{1}{2} \bar{\gamma}^{kl} \hat{D}_k \hat{D}_l \bar{\gamma}_{ij}
                    + \frac{1}{2} (\bar{\gamma}_{ki} \hat{D}_j \bar{\Lambda}^k + \bar{\gamma}_{kj} \hat{D}_i \bar{\Lambda}^k)
                    + \frac{1}{2} \Pi^k (\Pi_{ijk} + \Pi_{jik}) \\%
                    &\qquad+ \bar{\gamma}^{kl} (\Pi^m_{ki} \Pi_{jml} + \Pi^m_{kj} \Pi_{iml} + \Pi^m_{ik} \Pi_{mjl}) 
            \end{align}
        """)
        par.set_parval_from_str('reference_metric::CoordSystem', 'Cartesian')
        par.set_parval_from_str('BSSN.BSSN_quantities::LeaveRicciSymbolic',
                                'True')
        rfm.reference_metric()
        Brhs.BSSN_RHSs()
        par.set_parval_from_str('BSSN.BSSN_quantities::LeaveRicciSymbolic',
                                'False')
        Bq.RicciBar__gammabarDD_dHatD__DGammaUDD__DGammaU()
        assert_equal(
            {
                'h_rhsDD': h_rhsDD,
                'cf_rhs': cf_rhs,
                'trK_rhs': trK_rhs,
                'Lambdabar_rhsU': Lambdabar_rhsU,
                'a_rhsDD': a_rhsDD,
                'RbarDD': RbarDD
            }, {
                'h_rhsDD': Brhs.h_rhsDD,
                'cf_rhs': Brhs.cf_rhs,
                'trK_rhs': Brhs.trK_rhs,
                'Lambdabar_rhsU': Brhs.Lambdabar_rhsU,
                'a_rhsDD': Brhs.a_rhsDD,
                'RbarDD': Bq.RbarDD
            })
Пример #6
0
def BSSN_RHSs__generate_symbolic_expressions(
        LapseCondition="OnePlusLog",
        ShiftCondition="GammaDriving2ndOrder_Covariant",
        enable_KreissOliger_dissipation=True,
        enable_stress_energy_source_terms=False,
        leave_Ricci_symbolic=True):
    ######################################
    # START: GENERATE SYMBOLIC EXPRESSIONS
    starttime = print_msg_with_timing("BSSN_RHSs",
                                      msg="Symbolic",
                                      startstop="start")

    # Returns None if enable_stress_energy_source_terms==False; otherwise returns symb expressions for T4UU
    T4UU = register_stress_energy_source_terms_return_T4UU(
        enable_stress_energy_source_terms)

    # Evaluate BSSN RHSs:
    import BSSN.BSSN_quantities as Bq
    par.set_parval_from_str("BSSN.BSSN_quantities::LeaveRicciSymbolic",
                            str(leave_Ricci_symbolic))
    rhs.BSSN_RHSs()

    if enable_stress_energy_source_terms:
        import BSSN.BSSN_stress_energy_source_terms as Bsest
        Bsest.BSSN_source_terms_for_BSSN_RHSs(T4UU)
        rhs.trK_rhs += Bsest.sourceterm_trK_rhs
        for i in range(3):
            # Needed for Gamma-driving shift RHSs:
            rhs.Lambdabar_rhsU[i] += Bsest.sourceterm_Lambdabar_rhsU[i]
            # Needed for BSSN RHSs:
            rhs.lambda_rhsU[i] += Bsest.sourceterm_lambda_rhsU[i]
            for j in range(3):
                rhs.a_rhsDD[i][j] += Bsest.sourceterm_a_rhsDD[i][j]

    par.set_parval_from_str("BSSN.BSSN_gauge_RHSs::LapseEvolutionOption",
                            LapseCondition)
    par.set_parval_from_str("BSSN.BSSN_gauge_RHSs::ShiftEvolutionOption",
                            ShiftCondition)
    gaugerhs.BSSN_gauge_RHSs()  # Can depend on above RHSs
    # Restore BSSN.BSSN_quantities::LeaveRicciSymbolic to False
    par.set_parval_from_str("BSSN.BSSN_quantities::LeaveRicciSymbolic",
                            "False")

    # Add Kreiss-Oliger dissipation to the BSSN RHSs:
    if enable_KreissOliger_dissipation:
        thismodule = "KO_Dissipation"
        diss_strength = par.Cparameters(
            "REAL", thismodule, "diss_strength", 0.1
        )  # *Bq.cf # *Bq.cf*Bq.cf*Bq.cf # cf**1 is found better than cf**4 over the long term.

        alpha_dKOD = ixp.declarerank1("alpha_dKOD")
        cf_dKOD = ixp.declarerank1("cf_dKOD")
        trK_dKOD = ixp.declarerank1("trK_dKOD")
        betU_dKOD = ixp.declarerank2("betU_dKOD", "nosym")
        vetU_dKOD = ixp.declarerank2("vetU_dKOD", "nosym")
        lambdaU_dKOD = ixp.declarerank2("lambdaU_dKOD", "nosym")
        aDD_dKOD = ixp.declarerank3("aDD_dKOD", "sym01")
        hDD_dKOD = ixp.declarerank3("hDD_dKOD", "sym01")
        for k in range(3):
            gaugerhs.alpha_rhs += diss_strength * alpha_dKOD[k] * rfm.ReU[
                k]  # ReU[k] = 1/scalefactor_orthog_funcform[k]
            rhs.cf_rhs += diss_strength * cf_dKOD[k] * rfm.ReU[
                k]  # ReU[k] = 1/scalefactor_orthog_funcform[k]
            rhs.trK_rhs += diss_strength * trK_dKOD[k] * rfm.ReU[
                k]  # ReU[k] = 1/scalefactor_orthog_funcform[k]
            for i in range(3):
                if "2ndOrder" in ShiftCondition:
                    gaugerhs.bet_rhsU[
                        i] += diss_strength * betU_dKOD[i][k] * rfm.ReU[
                            k]  # ReU[k] = 1/scalefactor_orthog_funcform[k]
                gaugerhs.vet_rhsU[
                    i] += diss_strength * vetU_dKOD[i][k] * rfm.ReU[
                        k]  # ReU[k] = 1/scalefactor_orthog_funcform[k]
                rhs.lambda_rhsU[
                    i] += diss_strength * lambdaU_dKOD[i][k] * rfm.ReU[
                        k]  # ReU[k] = 1/scalefactor_orthog_funcform[k]
                for j in range(3):
                    rhs.a_rhsDD[i][
                        j] += diss_strength * aDD_dKOD[i][j][k] * rfm.ReU[
                            k]  # ReU[k] = 1/scalefactor_orthog_funcform[k]
                    rhs.h_rhsDD[i][
                        j] += diss_strength * hDD_dKOD[i][j][k] * rfm.ReU[
                            k]  # ReU[k] = 1/scalefactor_orthog_funcform[k]

    # We use betaU as our upwinding control vector:
    Bq.BSSN_basic_tensors()
    betaU = Bq.betaU

    # END: GENERATE SYMBOLIC EXPRESSIONS
    ######################################

    lhs_names = ["alpha", "cf", "trK"]
    rhs_exprs = [gaugerhs.alpha_rhs, rhs.cf_rhs, rhs.trK_rhs]
    for i in range(3):
        lhs_names.append("betU" + str(i))
        rhs_exprs.append(gaugerhs.bet_rhsU[i])
        lhs_names.append("lambdaU" + str(i))
        rhs_exprs.append(rhs.lambda_rhsU[i])
        lhs_names.append("vetU" + str(i))
        rhs_exprs.append(gaugerhs.vet_rhsU[i])
        for j in range(i, 3):
            lhs_names.append("aDD" + str(i) + str(j))
            rhs_exprs.append(rhs.a_rhsDD[i][j])
            lhs_names.append("hDD" + str(i) + str(j))
            rhs_exprs.append(rhs.h_rhsDD[i][j])

    # Sort the lhss list alphabetically, and rhss to match.
    #   This ensures the RHSs are evaluated in the same order
    #   they're allocated in memory:
    lhs_names, rhs_exprs = [
        list(x) for x in zip(
            *sorted(zip(lhs_names, rhs_exprs), key=lambda pair: pair[0]))
    ]

    # Declare the list of lhrh's
    BSSN_RHSs_SymbExpressions = []
    for var in range(len(lhs_names)):
        BSSN_RHSs_SymbExpressions.append(
            lhrh(lhs=gri.gfaccess("rhs_gfs", lhs_names[var]),
                 rhs=rhs_exprs[var]))

    print_msg_with_timing("BSSN_RHSs",
                          msg="Symbolic",
                          startstop="stop",
                          starttime=starttime)
    return [betaU, BSSN_RHSs_SymbExpressions]
Пример #7
0
def BSSN_gauge_RHSs():
    # Step 1.d: Set spatial dimension (must be 3 for BSSN, as BSSN is
    #           a 3+1-dimensional decomposition of the general
    #           relativistic field equations)
    DIM = 3

    # Step 1.e: Given the chosen coordinate system, set up
    #           corresponding reference metric and needed
    #           reference metric quantities
    # The following function call sets up the reference metric
    #    and related quantities, including rescaling matrices ReDD,
    #    ReU, and hatted quantities.
    rfm.reference_metric()

    # Step 1.f: Define needed BSSN quantities:
    # Declare scalars & tensors (in terms of rescaled BSSN quantities)
    Bq.BSSN_basic_tensors()
    Bq.betaU_derivs()
    # Declare BSSN_RHSs (excluding the time evolution equations for the gauge conditions)
    Brhs.BSSN_RHSs()

    # Step 2.a: The 1+log lapse condition:
    #   \partial_t \alpha = \beta^i \alpha_{,i} - 2*\alpha*K
    # First import expressions from BSSN_quantities
    cf = Bq.cf
    trK = Bq.trK
    alpha = Bq.alpha
    betaU = Bq.betaU

    # Implement the 1+log lapse condition
    global alpha_rhs
    alpha_rhs = sp.sympify(0)
    if par.parval_from_str(thismodule +
                           "::LapseEvolutionOption") == "OnePlusLog":
        alpha_rhs = -2 * alpha * trK
        alpha_dupD = ixp.declarerank1("alpha_dupD")
        for i in range(DIM):
            alpha_rhs += betaU[i] * alpha_dupD[i]

    # Step 2.b: Implement the harmonic slicing lapse condition
    elif par.parval_from_str(thismodule +
                             "::LapseEvolutionOption") == "HarmonicSlicing":
        if par.parval_from_str(
                "BSSN.BSSN_quantities::EvolvedConformalFactor_cf") == "W":
            alpha_rhs = -3 * cf**(-4) * Brhs.cf_rhs
        elif par.parval_from_str(
                "BSSN.BSSN_quantities::EvolvedConformalFactor_cf") == "phi":
            alpha_rhs = 6 * sp.exp(6 * cf) * Brhs.cf_rhs
        else:
            print(
                "Error LapseEvolutionOption==HarmonicSlicing unsupported for EvolvedConformalFactor_cf!=(W or phi)"
            )
            exit(1)

    # Step 2.c: Frozen lapse
    #    \partial_t \alpha = 0
    elif par.parval_from_str(thismodule +
                             "::LapseEvolutionOption") == "Frozen":
        alpha_rhs = sp.sympify(0)

    else:
        print("Error: " + thismodule + "::LapseEvolutionOption == " +
              par.parval_from_str(thismodule + "::LapseEvolutionOption") +
              " not supported!")
        exit(1)

    # Step 3.a: Set \partial_t \beta^i
    # First import expressions from BSSN_quantities
    BU = Bq.BU
    betU = Bq.betU
    betaU_dupD = Bq.betaU_dupD
    # Define needed quantities
    beta_rhsU = ixp.zerorank1()
    B_rhsU = ixp.zerorank1()
    if par.parval_from_str(
            thismodule +
            "::ShiftEvolutionOption") == "GammaDriving2ndOrder_NoCovariant":
        # Step 3.a.i: Compute right-hand side of beta^i
        # *  \partial_t \beta^i = \beta^j \beta^i_{,j} + B^i
        for i in range(DIM):
            beta_rhsU[i] += BU[i]
            for j in range(DIM):
                beta_rhsU[i] += betaU[j] * betaU_dupD[i][j]
        # Compute right-hand side of B^i:
        eta = par.Cparameters("REAL", thismodule, ["eta"])

        # Step 3.a.ii: Compute right-hand side of B^i
        # *  \partial_t B^i     = \beta^j B^i_{,j} + 3/4 * \partial_0 \Lambda^i - eta B^i
        # Step 3.a.iii: Define BU_dupD, in terms of derivative of rescaled variable \bet^i
        BU_dupD = ixp.zerorank2()
        betU_dupD = ixp.declarerank2("betU_dupD", "nosym")
        for i in range(DIM):
            for j in range(DIM):
                BU_dupD[i][j] = betU_dupD[i][j] * rfm.ReU[i] + betU[
                    i] * rfm.ReUdD[i][j]

        # Step 3.a.iv: Compute \partial_0 \bar{\Lambda}^i = (\partial_t - \beta^i \partial_i) \bar{\Lambda}^j
        Lambdabar_partial0 = ixp.zerorank1()
        for i in range(DIM):
            Lambdabar_partial0[i] = Brhs.Lambdabar_rhsU[i]
        for i in range(DIM):
            for j in range(DIM):
                Lambdabar_partial0[j] += -betaU[i] * Brhs.LambdabarU_dupD[j][i]

        # Step 3.a.v: Evaluate RHS of B^i:
        for i in range(DIM):
            B_rhsU[i] += sp.Rational(3,
                                     4) * Lambdabar_partial0[i] - eta * BU[i]
            for j in range(DIM):
                B_rhsU[i] += betaU[j] * BU_dupD[i][j]

    # Step 3.b: The right-hand side of the \partial_t \beta^i equation
    if par.parval_from_str(
            thismodule +
            "::ShiftEvolutionOption") == "GammaDriving2ndOrder_Covariant":
        # Step 3.b Option 2: \partial_t \beta^i = \left[\beta^j \bar{D}_j \beta^i\right] + B^{i}
        # First we need GammabarUDD, defined in Bq.gammabar__inverse_and_derivs()
        Bq.gammabar__inverse_and_derivs()
        GammabarUDD = Bq.GammabarUDD
        # Then compute right-hand side:
        # Term 1: \beta^j \beta^i_{,j}
        for i in range(DIM):
            for j in range(DIM):
                beta_rhsU[i] += betaU[j] * betaU_dupD[i][j]

        # Term 2: \beta^j \bar{\Gamma}^i_{mj} \beta^m
        for i in range(DIM):
            for j in range(DIM):
                for m in range(DIM):
                    beta_rhsU[i] += betaU[j] * GammabarUDD[i][m][j] * betaU[m]
        # Term 3: B^i
        for i in range(DIM):
            beta_rhsU[i] += BU[i]

    if par.parval_from_str(
            thismodule +
            "::ShiftEvolutionOption") == "GammaDriving2ndOrder_Covariant":
        # Step 3.c: Covariant option:
        #  \partial_t B^i = \beta^j \bar{D}_j B^i
        #               + \frac{3}{4} ( \partial_t \bar{\Lambda}^{i} - \beta^j \bar{D}_j \bar{\Lambda}^{i} )
        #               - \eta B^{i}
        #                 = \beta^j B^i_{,j} + \beta^j \bar{\Gamma}^i_{mj} B^m
        #               + \frac{3}{4}[ \partial_t \bar{\Lambda}^{i}
        #                            - \beta^j (\bar{\Lambda}^i_{,j} + \bar{\Gamma}^i_{mj} \bar{\Lambda}^m)]
        #               - \eta B^{i}
        # Term 1, part a: First compute B^i_{,j} using upwinded derivative
        BU_dupD = ixp.zerorank2()
        betU_dupD = ixp.declarerank2("betU_dupD", "nosym")
        for i in range(DIM):
            for j in range(DIM):
                BU_dupD[i][j] = betU_dupD[i][j] * rfm.ReU[i] + betU[
                    i] * rfm.ReUdD[i][j]
        # Term 1: \beta^j B^i_{,j}
        for i in range(DIM):
            for j in range(DIM):
                B_rhsU[i] += betaU[j] * BU_dupD[i][j]
        # Term 2: \beta^j \bar{\Gamma}^i_{mj} B^m
        for i in range(DIM):
            for j in range(DIM):
                for m in range(DIM):
                    B_rhsU[i] += betaU[j] * GammabarUDD[i][m][j] * BU[m]
        # Term 3: \frac{3}{4}\partial_t \bar{\Lambda}^{i}
        for i in range(DIM):
            B_rhsU[i] += sp.Rational(3, 4) * Brhs.Lambdabar_rhsU[i]
        # Term 4: -\frac{3}{4}\beta^j \bar{\Lambda}^i_{,j}
        for i in range(DIM):
            for j in range(DIM):
                B_rhsU[i] += -sp.Rational(
                    3, 4) * betaU[j] * Brhs.LambdabarU_dupD[i][j]
        # Term 5: -\frac{3}{4}\beta^j \bar{\Gamma}^i_{mj} \bar{\Lambda}^m
        for i in range(DIM):
            for j in range(DIM):
                for m in range(DIM):
                    B_rhsU[i] += -sp.Rational(3, 4) * betaU[j] * GammabarUDD[
                        i][m][j] * Bq.LambdabarU[m]
        # Term 6: - \eta B^i
        # eta is a free parameter; we declare it here:
        eta = par.Cparameters("REAL", thismodule, ["eta"])
        for i in range(DIM):
            B_rhsU[i] += -eta * BU[i]

    # Step 4: Rescale the BSSN gauge RHS quantities so that the evolved
    #         variables may remain smooth across coord singularities
    global vet_rhsU, bet_rhsU
    vet_rhsU = ixp.zerorank1()
    bet_rhsU = ixp.zerorank1()
    for i in range(DIM):
        vet_rhsU[i] = beta_rhsU[i] / rfm.ReU[i]
        bet_rhsU[i] = B_rhsU[i] / rfm.ReU[i]