
// Make newform 45.4.f.a in Magma, downloaded from the LMFDB on 23 April 2024.
// To make the character of type GrpDrchElt, type "MakeCharacter_45_f();"
// To make the character of type GrpDrchElt with Codomain the HeckeField, type "MakeCharacter_45_f_Hecke();"
// To make the coeffs of the qexp of the newform in the Hecke field type "qexpCoeffs();"
// To make the newform (type ModFrm), type "MakeNewformModFrm_45_4_f_a();".
// This may take a long time!  To see verbose output, uncomment the SetVerbose lines below.
// The precision argument determines an initial guess on how many Fourier coefficients to use.
// This guess is increased enough to uniquely determine the newform.
// To make the Hecke irreducible modular symbols subspace (type ModSym)
// containing the newform, type "MakeNewformModSym_45_4_f_a();".
// This may take a long time!  To see verbose output, uncomment the SetVerbose line below.
// The default sign is -1.  You can change this with the optional parameter "sign".
function ConvertToHeckeField(input: pass_field := false, Kf := [])
    if not pass_field then
        poly := [506944, 0, 126224, 0, 3889, 0, -512, 0, -14, 0, -16, 0, 1];
        Kf := NumberField(Polynomial([elt : elt in poly]));
        AssignNames(~Kf, ["nu"]);
    end if;
    Rf_num := [[1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0], [418024, 0, 83197, 0, 3248, 0, 634, 0, -56, 0, -3, 0], [-1578712, 0, -1896111, 0, -356014, 0, -4502, 0, 2538, 0, -71, 0], [78379688, 0, 22729229, 0, -2560724, 0, 158738, 0, -22972, 0, 1029, 0], [559571096, 0, 44277523, 0, -2434608, 0, 167406, 0, -110024, 0, 5723, 0], [-51726904, 0, -16244903, 0, -1362480, 0, -23478, 0, -2936, 0, 1265, 0], [0, -93476563288, 0, -12758183579, 0, -253832976, 0, -76074438, 0, 12179272, 0, 113621], [0, -1295931240, 0, -1219736029, 0, 10214960, 0, -20705978, 0, 1391000, 0, 28451], [0, -554840616, 0, -79774373, 0, 5223568, 0, -577306, 0, 146104, 0, -6773], [0, 28260515592, 0, 6018524881, 0, 1380835984, 0, -15466318, 0, 7804552, 0, -1093919], [0, -11971272, 0, 8928141, 0, 745404, 0, 18534, 0, 7908, 0, -1095], [0, -669132280, 0, -5216047, 0, 11892160, 0, -524974, 0, 123320, 0, -9087]];
    Rf_basisdens := [1, 182400, 3620640, 9051600, 18103200, 2896512, 25778956800, 2577895680, 226131200, 25778956800, 21482464, 135678720];
    Rf_basisnums := ChangeUniverse([[z : z in elt] : elt in Rf_num], Kf);
    Rfbasis := [Rf_basisnums[i]/Rf_basisdens[i] : i in [1..Degree(Kf)]];
    inp_vec := Vector(Rfbasis)*ChangeRing(Transpose(Matrix([[elt : elt in row] : row in input])),Kf);
    return Eltseq(inp_vec);
end function;


// To make the character of type GrpDrchElt, type "MakeCharacter_45_f();"
function MakeCharacter_45_f()
    N := 45;
    order := 4;
    char_gens := [11, 37];
    v := [2, 3];
    // chi(gens[i]) = zeta^v[i]
    assert UnitGenerators(DirichletGroup(N)) eq char_gens;
    F := CyclotomicField(order);
    chi := DirichletCharacterFromValuesOnUnitGenerators(DirichletGroup(N,F),[F|F.1^e:e in v]);
    return MinimalBaseRingCharacter(chi);
end function;

// To make the character of type GrpDrchElt with Codomain the HeckeField, type "MakeCharacter_45_f_Hecke();"
function MakeCharacter_45_f_Hecke(Kf)
    N := 45;
    order := 4;
    char_gens := [11, 37];
    char_values := [[-1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0], [0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0]];
    assert UnitGenerators(DirichletGroup(N)) eq char_gens;
    values := ConvertToHeckeField(char_values : pass_field := true, Kf := Kf); // the value of chi on the gens as elements in the Hecke field
    F := Universe(values);// the Hecke field
    chi := DirichletCharacterFromValuesOnUnitGenerators(DirichletGroup(N,F),values);
    return chi;
end function;


function ExtendMultiplicatively(weight, aps, character)
    prec := NextPrime(NthPrime(#aps)) - 1; // we will able to figure out a_0 ... a_prec
    primes := PrimesUpTo(prec);
    prime_powers := primes;
    assert #primes eq #aps;
    log_prec := Floor(Log(prec)/Log(2)); // prec < 2^(log_prec+1)
    F := Universe(aps);
    FXY<X, Y> := PolynomialRing(F, 2);
    // 1/(1 - a_p T + p^(weight - 1) * char(p) T^2) = 1 + a_p T + a_{p^2} T^2 + ...
    R<T> := PowerSeriesRing(FXY : Precision := log_prec + 1);
    recursion := Coefficients(1/(1 - X*T + Y*T^2));
    coeffs := [F!0: i in [1..(prec+1)]];
    coeffs[1] := 1; //a_1
    for i := 1 to #primes do
        p := primes[i];
        coeffs[p] := aps[i];
        b := p^(weight - 1) * F!character(p);
        r := 2;
        p_power := p * p;
        //deals with powers of p
        while p_power le prec do
            Append(~prime_powers, p_power);
            coeffs[p_power] := Evaluate(recursion[r + 1], [aps[i], b]);
            p_power *:= p;
            r +:= 1;
        end while;    
    end for;
    Sort(~prime_powers);
    for pp in prime_powers do
        for k := 1 to Floor(prec/pp) do
            if GCD(k, pp) eq 1 then
                coeffs[pp*k] := coeffs[pp]*coeffs[k];
            end if;
        end for;
    end for;
    return coeffs;
end function;


function qexpCoeffs()
    // To make the coeffs of the qexp of the newform in the Hecke field type "qexpCoeffs();"
    weight := 4;
    raw_aps := [[0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0], [0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0], [0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1], [2, 2, 0, 0, -1, 0, 0, 0, 0, 0, 0, 0], [0, 0, 0, 0, 0, 0, -7, -1, 0, 7, -3, 1], [-9, 9, -2, 3, 0, 2, 0, 0, 0, 0, 0, 0], [0, 0, 0, 0, 0, 0, 8, 0, 12, 0, 12, -2], [0, -20, 0, 5, 5, 4, 0, 0, 0, 0, 0, 0], [0, 0, 0, 0, 0, 0, 0, -12, 2, 8, -2, 0], [0, 0, 0, 0, 0, 0, -25, 5, -4, -25, 0, 5], [-104, 0, -4, 5, -5, 0, 0, 0, 0, 0, 0, 0], [69, 69, 8, 0, -7, 8, 0, 0, 0, 0, 0, 0], [0, 0, 0, 0, 0, 0, 38, -16, 0, -38, -29, 16], [-8, 8, 16, -14, 0, -16, 0, 0, 0, 0, 0, 0], [0, 0, 0, 0, 0, 0, 58, 0, 23, 0, 23, -18], [0, 0, 0, 0, 0, 0, 0, 20, -5, 34, 5, 0], [0, 0, 0, 0, 0, 0, -41, -17, 31, -41, 0, -17], [8, 0, -48, 15, -15, 0, 0, 0, 0, 0, 0, 0], [136, 136, -44, 0, 2, -44, 0, 0, 0, 0, 0, 0], [0, 0, 0, 0, 0, 0, -16, 32, 0, 16, -4, -32], [331, -331, -18, -12, 0, 18, 0, 0, 0, 0, 0, 0], [0, 672, 0, 25, 25, 28, 0, 0, 0, 0, 0, 0], [0, 0, 0, 0, 0, 0, 0, -2, -153, 78, 153, 0], [0, 0, 0, 0, 0, 0, 36, 42, 163, 36, 0, 42], [231, 231, -50, 0, -78, -50, 0, 0, 0, 0, 0, 0], [0, 0, 0, 0, 0, 0, 83, 29, 0, -83, -50, -29], [70, -70, 32, 5, 0, -32, 0, 0, 0, 0, 0, 0], [0, 0, 0, 0, 0, 0, -118, 0, -91, 0, -91, -14], [0, 0, 0, 15, 15, 96, 0, 0, 0, 0, 0, 0], [0, 0, 0, 0, 0, 0, 0, 78, -93, -220, 93, 0], [-450, -450, 56, 0, 95, 56, 0, 0, 0, 0, 0, 0], [0, 0, 0, 0, 0, 0, 59, 17, 0, -59, 79, -17], [0, 0, 0, 0, 0, 0, 4, 0, 197, 0, 197, 18], [0, 408, 0, -10, -10, -148, 0, 0, 0, 0, 0, 0], [0, 0, 0, 0, 0, 0, -35, 85, 164, -35, 0, 85], [-1652, 0, -4, 50, -50, 0, 0, 0, 0, 0, 0, 0], [335, 335, 56, 0, -15, 56, 0, 0, 0, 0, 0, 0], [372, -372, -76, 46, 0, 76, 0, 0, 0, 0, 0, 0], [0, 0, 0, 0, 0, 0, -84, 0, 168, 0, 168, 32], [0, 0, 0, 0, 0, 0, 0, -134, 49, 384, -49, 0], [0, 0, 0, 0, 0, 0, 459, 63, 375, 459, 0, 63], [-656, 0, 32, 35, -35, 0, 0, 0, 0, 0, 0, 0], [0, 0, 0, 0, 0, 0, -280, -160, 0, 280, 168, 160], [-999, 999, -200, 138, 0, 200, 0, 0, 0, 0, 0, 0], [0, 0, 0, 0, 0, 0, -136, 0, 459, 0, 459, -74], [0, 20, 0, -20, -20, -100, 0, 0, 0, 0, 0, 0], [896, 0, -12, -180, 180, 0, 0, 0, 0, 0, 0, 0], [1530, -1530, 60, 95, 0, -60, 0, 0, 0, 0, 0, 0], [0, 0, 0, 0, 0, 0, 52, 0, -270, 0, -270, -300], [0, -234, 0, 20, 20, -196, 0, 0, 0, 0, 0, 0], [0, 0, 0, 0, 0, 0, 0, -34, 154, -308, -154, 0], [0, 0, 0, 0, 0, 0, -320, 220, 36, -320, 0, 220], [-1550, 0, 68, -160, 160, 0, 0, 0, 0, 0, 0, 0], [0, 0, 0, 0, 0, 0, 317, 191, 0, -317, -275, -191], [0, 0, 0, 0, 0, 0, 540, 0, 111, 0, 111, 134], [0, 0, 0, 0, 0, 0, 0, -44, -306, -288, 306, 0], [0, 0, 0, 0, 0, 0, 237, 69, -586, 237, 0, 69], [3324, 0, 196, 70, -70, 0, 0, 0, 0, 0, 0, 0], [2611, 2611, 110, 0, 247, 110, 0, 0, 0, 0, 0, 0], [0, 0, 0, 0, 0, 0, 404, 302, 0, -404, 355, -302], [812, -812, -132, -284, 0, 132, 0, 0, 0, 0, 0, 0], [0, 0, 0, 0, 0, 0, 0, -54, 309, -856, -309, 0], [-3172, -3172, -452, 0, -314, -452, 0, 0, 0, 0, 0, 0], [0, 0, 0, 0, 0, 0, -202, -346, 0, 202, 1074, 346], [-701, 701, 280, 142, 0, -280, 0, 0, 0, 0, 0, 0], [0, 0, 0, 0, 0, 0, -1418, 0, -203, 0, -203, -372], [4148, 0, -396, 165, -165, 0, 0, 0, 0, 0, 0, 0], [-255, -255, -150, 0, 280, -150, 0, 0, 0, 0, 0, 0], [0, 0, 0, 0, 0, 0, 1296, 0, -840, 0, -840, 440], [0, -824, 0, 345, 345, 608, 0, 0, 0, 0, 0, 0], [0, 0, 0, 0, 0, 0, 0, 22, 498, 1740, -498, 0], [0, 0, 0, 0, 0, 0, -570, -90, 530, -570, 0, -90], [-3098, -3098, 428, 0, -131, 428, 0, 0, 0, 0, 0, 0], [-4997, 4997, 104, 59, 0, -104, 0, 0, 0, 0, 0, 0], [0, 2936, 0, -110, -110, 188, 0, 0, 0, 0, 0, 0], [0, 0, 0, 0, 0, 0, 0, -618, 523, -1126, -523, 0], [0, 0, 0, 0, 0, 0, -301, 83, -1700, -301, 0, 83], [-1169, -1169, -432, 0, -693, -432, 0, 0, 0, 0, 0, 0], [0, 0, 0, 0, 0, 0, -1342, -346, 0, 1342, -1823, 346], [0, -3976, 0, 330, 330, 448, 0, 0, 0, 0, 0, 0], [0, 0, 0, 0, 0, 0, -2045, 295, -933, -2045, 0, 295], [-4390, 0, 228, -300, 300, 0, 0, 0, 0, 0, 0, 0], [0, 0, 0, 0, 0, 0, 1760, 80, 0, -1760, 1852, -80], [-4417, 4417, 64, -46, 0, -64, 0, 0, 0, 0, 0, 0], [0, -6444, 0, 310, 310, 292, 0, 0, 0, 0, 0, 0], [0, 0, 0, 0, 0, 0, 0, -332, -518, -1596, 518, 0], [0, 0, 0, 0, 0, 0, -966, -102, -2079, -966, 0, -102], [5355, 5355, 70, 0, -210, 70, 0, 0, 0, 0, 0, 0], [0, 0, 0, 0, 0, 0, -397, -91, 0, 397, -2776, 91], [-5630, 5630, -220, 425, 0, 220, 0, 0, 0, 0, 0, 0], [0, 0, 0, 0, 0, 0, 1046, 0, -1169, 0, -1169, -986], [0, 0, 0, 0, 0, 0, 1436, -268, 1480, 1436, 0, -268], [-6850, -6850, 424, 0, 175, 424, 0, 0, 0, 0, 0, 0], [0, 0, 0, 0, 0, 0, -1963, 731, 0, 1963, 837, -731], [0, 4564, 0, -515, -515, -780, 0, 0, 0, 0, 0, 0], [0, 0, 0, 0, 0, 0, 0, 26, 789, 3526, -789, 0], [0, 0, 0, 0, 0, 0, 925, 535, -416, 925, 0, 535], [0, 0, 0, 0, 0, 0, 1514, -538, 0, -1514, -137, 538], [4512, -4512, -232, -524, 0, 232, 0, 0, 0, 0, 0, 0], [5184, 0, -272, 145, -145, 0, 0, 0, 0, 0, 0, 0], [3900, 3900, -680, 0, -120, -680, 0, 0, 0, 0, 0, 0], [0, 0, 0, 0, 0, 0, 50, 0, 2043, 0, 2043, 1192], [0, 0, 0, 0, 0, 0, 0, 240, -2460, 320, 2460, 0], [0, 0, 0, 0, 0, 0, 398, 1286, -5, 398, 0, 1286], [3092, 0, -228, -135, 135, 0, 0, 0, 0, 0, 0, 0], [487, 487, 552, 0, 564, 552, 0, 0, 0, 0, 0, 0], [0, 0, 0, 0, 0, 0, -2606, 0, -1187, 0, -1187, 402], [0, 0, 0, 0, 0, 0, 0, -826, 431, -212, -431, 0], [0, 0, 0, 0, 0, 0, -428, -956, 488, -428, 0, -956], [-10792, 0, -288, 120, -120, 0, 0, 0, 0, 0, 0, 0], [-11022, -11022, 264, 0, 751, 264, 0, 0, 0, 0, 0, 0], [7261, -7261, -192, 543, 0, 192, 0, 0, 0, 0, 0, 0], [0, 0, 0, 0, 0, 0, -2268, 0, -74, 0, -74, 614], [0, 6672, 0, 100, 100, -1460, 0, 0, 0, 0, 0, 0], [8880, 0, 2668, -785, 785, 0, 0, 0, 0, 0, 0, 0], [0, 0, 0, 0, 0, 0, 2726, 608, 0, -2726, -497, -608], [3528, -3528, 412, 444, 0, -412, 0, 0, 0, 0, 0, 0], [0, 0, 0, 0, 0, 0, 314, 0, -1913, 0, -1913, -602], [0, 0, 0, 0, 0, 0, 0, 864, -949, -5254, 949, 0], [0, 0, 0, 0, 0, 0, 785, -295, 3753, 785, 0, -295], [-11320, 0, 384, -15, 15, 0, 0, 0, 0, 0, 0, 0], [-5839, 5839, -448, 798, 0, 448, 0, 0, 0, 0, 0, 0], [0, 0, 0, 0, 0, 0, 358, 0, 101, 0, 101, 1704], [0, 0, 0, 0, 0, 0, 0, 830, -3785, -1586, 3785, 0], [3748, 0, 1892, -685, 685, 0, 0, 0, 0, 0, 0, 0], [0, 0, 0, 0, 0, 0, -1261, -1033, 0, 1261, -3336, 1033], [0, -1286, 0, -840, -840, -1132, 0, 0, 0, 0, 0, 0], [0, 0, 0, 0, 0, 0, 876, 1152, -2564, 876, 0, 1152], [-3438, -3438, -1376, 0, -951, -1376, 0, 0, 0, 0, 0, 0], [5151, -5151, -1274, 633, 0, 1274, 0, 0, 0, 0, 0, 0], [0, 7580, 0, 475, 475, 692, 0, 0, 0, 0, 0, 0], [0, 0, 0, 0, 0, 0, 0, -1842, -413, -838, 413, 0], [-12424, 0, -1380, -45, 45, 0, 0, 0, 0, 0, 0, 0], [-1419, -1419, 482, 0, 917, 482, 0, 0, 0, 0, 0, 0], [0, 0, 0, 0, 0, 0, -3658, 266, 0, 3658, -3357, -266], [0, 5464, 0, 970, 970, -384, 0, 0, 0, 0, 0, 0], [0, 0, 0, 0, 0, 0, 0, -1588, -1727, 2350, 1727, 0], [12236, 12236, 992, 0, 702, 992, 0, 0, 0, 0, 0, 0], [0, 0, 0, 0, 0, 0, 4248, 0, 2685, 0, 2685, -910], [0, 0, 0, 0, 0, 0, 3102, 624, 4195, 3102, 0, 624], [-6800, 0, -2356, 620, -620, 0, 0, 0, 0, 0, 0, 0], [0, 0, 0, 0, 0, 0, 1121, 293, 0, -1121, -2544, -293], [6730, -6730, 476, -865, 0, -476, 0, 0, 0, 0, 0, 0], [0, 0, 0, 0, 0, 0, 1076, 0, -146, 0, -146, -1964], [0, 19120, 0, 185, 185, 2032, 0, 0, 0, 0, 0, 0], [0, 0, 0, 0, 0, 0, -5434, 1022, -5062, -5434, 0, 1022], [-18957, 18957, 960, -1591, 0, -960, 0, 0, 0, 0, 0, 0], [0, 0, 0, 0, 0, 0, 4144, 0, 1224, 0, 1224, -1554], [0, 448, 0, -680, -680, 804, 0, 0, 0, 0, 0, 0], [0, 0, 0, 0, 0, 0, 0, 2960, 1540, 3604, -1540, 0], [16937, 16937, -856, 0, -1161, -856, 0, 0, 0, 0, 0, 0], [0, 0, 0, 0, 0, 0, 728, 554, 0, -728, 1243, -554], [18372, -18372, -892, 886, 0, 892, 0, 0, 0, 0, 0, 0], [0, 0, 0, 0, 0, 0, 1620, 0, -1580, 0, -1580, 200], [8480, 8480, 612, 0, -910, 612, 0, 0, 0, 0, 0, 0], [0, 0, 0, 0, 0, 0, 2210, -1270, 0, -2210, -1682, 1270], [0, 2096, 0, -1235, -1235, -412, 0, 0, 0, 0, 0, 0], [0, 0, 0, 0, 0, 0, -298, -586, 141, -298, 0, -586], [-14307, -14307, -736, 0, -484, -736, 0, 0, 0, 0, 0, 0], [0, 0, 0, 0, 0, 0, 2861, 83, 0, -2861, 1824, -83], [0, 0, 0, 0, 0, 0, 1636, 0, 2962, 0, 2962, 2268], [0, 0, 0, 0, 0, 0, 0, -3046, -1719, -1796, 1719, 0], [-2242, -2242, -676, 0, -549, -676, 0, 0, 0, 0, 0, 0], [0, 0, 0, 0, 0, 0, 3653, 2159, 0, -3653, -619, -2159], [0, 0, 0, 0, 0, 0, 10056, 0, 1252, 0, 1252, -1282], [0, 0, 0, 0, 0, 0, 0, -494, 1289, -6594, -1289, 0], [34324, 0, -1588, 650, -650, 0, 0, 0, 0, 0, 0, 0], [-3915, -3915, -1616, 0, 1395, -1616, 0, 0, 0, 0, 0, 0]];
    aps := ConvertToHeckeField(raw_aps);
    chi := MakeCharacter_45_f_Hecke(Universe(aps));
    return ExtendMultiplicatively(weight, aps, chi);
end function;


// To make the newform (type ModFrm), type "MakeNewformModFrm_45_4_f_a();".
// This may take a long time!  To see verbose output, uncomment the SetVerbose lines below.
// The precision argument determines an initial guess on how many Fourier coefficients to use.
// This guess is increased enough to uniquely determine the newform.
function MakeNewformModFrm_45_4_f_a(:prec:=12)
    chi := MakeCharacter_45_f();
    f_vec := qexpCoeffs();
    Kf := Universe(f_vec);
    // SetVerbose("ModularForms", true);
    // SetVerbose("ModularSymbols", true);
    S := CuspidalSubspace(ModularForms(chi, 4));
    S := BaseChange(S, Kf);
    maxprec := NextPrime(997) - 1;
    while true do
        trunc_vec := Vector(Kf, [0] cat [f_vec[i]: i in [1..prec]]);
        B := Basis(S, prec + 1);
        S_basismat := Matrix([AbsEltseq(g): g in B]);
        if Rank(S_basismat) eq Min(NumberOfRows(S_basismat), NumberOfColumns(S_basismat)) then
            S_basismat := ChangeRing(S_basismat,Kf);
            f_lincom := Solution(S_basismat,trunc_vec);
            f := &+[f_lincom[i]*Basis(S)[i] : i in [1..#Basis(S)]];
            return f;
        end if;
        error if prec eq maxprec, "Unable to distinguish newform within newspace";
        prec := Min(Ceiling(1.25 * prec), maxprec);
    end while;
end function;


// To make the Hecke irreducible modular symbols subspace (type ModSym)
// containing the newform, type "MakeNewformModSym_45_4_f_a();".
// This may take a long time!  To see verbose output, uncomment the SetVerbose line below.
// The default sign is -1.  You can change this with the optional parameter "sign".
function MakeNewformModSym_45_4_f_a( : sign := -1)
    R<x> := PolynomialRing(Rationals());
    chi := MakeCharacter_45_f();
    // SetVerbose("ModularSymbols", true);
    Snew := NewSubspace(CuspidalSubspace(ModularSymbols(chi,4,sign)));
    Vf := Kernel([],Snew);
    return Vf;
end function;