
// Make newform 2205.4.a.x in Magma, downloaded from the LMFDB on 20 April 2024.
// To make the character of type GrpDrchElt, type "MakeCharacter_2205_a();"
// To make the coeffs of the qexp of the newform in the Hecke field type "qexpCoeffs();"
// To make the newform (type ModFrm), type "MakeNewformModFrm_2205_4_a_x();".
// 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_2205_4_a_x();".
// 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 := [-11, 0, 1];
        Kf := NumberField(Polynomial([elt : elt in poly]));
        AssignNames(~Kf, ["nu"]);
    end if;
    Rfbasis := [Kf.1^i : i in [0..Degree(Kf)-1]];
    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_2205_a();"
function MakeCharacter_2205_a()
    N := 2205;
    order := 1;
    char_gens := [1226, 442, 1081];
    v := [1, 1, 1];
    // 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;

function MakeCharacter_2205_a_Hecke(Kf)
    return MakeCharacter_2205_a();
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 := [[-1, 1], [0, 0], [5, 0], [0, 0], [-33, -4], [-5, 20], [35, 20], [-70, 20], [8, -28], [129, -48], [10, -60], [164, -44], [150, 100], [-58, -12], [-15, 40], [-270, -120], [190, -40], [-540, -60], [234, 96], [528, 64], [430, -200], [79, -348], [20, 200], [-120, -380], [-815, 180], [-1010, -140], [15, 240], [90, -160], [-951, -288], [-1188, 68], [-1834, 64], [-120, -380], [1220, 220], [-2800, 0], [134, 392], [-513, -444], [490, -160], [-2760, -360], [1125, 680], [2875, 100], [-116, -400], [1970, -320], [-153, -700], [2512, 308], [-714, 804], [-4330, 80], [-4657, 100], [-1405, 720], [1125, -840], [110, 140], [-2088, 1328], [2001, 500], [-2380, -20], [540, -1040], [1230, -320], [-1558, 1448], [-1920, -280], [1060, 540], [-620, 880], [-723, -1624], [-1875, -1200], [-5865, 220], [285, -720], [-3310, -740], [2355, -300], [-6386, 376], [-748, 776], [-1040, 360], [-3444, -276], [-1490, -60], [-5845, 580], [2576, 88], [-11105, -120], [2128, 892], [3104, -648], [-4080, 2160], [7419, -328], [4505, 2300], [5763, -1656], [1950, -1800], [-1410, 1160], [-1647, -936], [3683, -3500], [5650, 1760], [2780, 1920], [-3390, 460], [-5791, 392], [-4646, -2924], [-15620, 320], [6880, -2620], [4655, 400], [-1540, 3940], [6956, 2664], [-8143, -1484], [-5211, -4500], [1415, -200], [-3320, 4720], [9630, -2380], [-8320, 2080], [-4893, 3216], [-6316, 716], [7164, -64], [18580, 1720], [16814, 1432], [10028, -4136], [16015, 1860], [10340, 80], [-555, 2060], [4359, 1692], [13210, 3440], [-6875, -1320], [-17522, 672], [396, 5184], [-1540, 7540], [-323, -1724], [-13782, -3416], [-5085, 600], [6260, 880], [18750, -1300], [579, 700], [1300, -3400], [5040, 4740], [-13175, 4940], [-7292, 892], [11660, 840], [11473, -3200], [-17929, 3000], [-3920, -8980], [560, 8960], [-15185, -1260], [-6131, 9372], [-1530, 2920], [1327, -1700], [-7864, 3464], [26480, -1780], [14210, -3360], [3365, -6860], [-20545, -6880], [10035, 2140], [2699, -488], [-10440, -2760], [-15737, 3200], [-1682, -3468], [2856, -8296], [29690, -340], [3180, 8420], [16190, 1320], [-14950, 2560], [-28580, -5920], [6198, 7692], [6750, 5700], [-8960, 6160], [21652, 5268], [3120, -5640], [9620, 5420], [9408, 1504], [-14489, 7468], [-3450, 3000], [-8635, 5700], [24380, 3020], [-10410, -5060], [-25462, -7388], [-28430, 3520], [-12610, -7540], [-8646, 10956], [-15325, -2240], [-468, -16584], [10605, 1380], [49001, 2888], [-6630, -11160], [-15764, 10168], [38650, -3400], [7827, 11676], [26920, -2880], [6150, -16500], [16260, 3840], [-41687, -6956], [30843, 0], [-26900, 2320], [-15600, 3900], [-10616, 5276], [-3240, -4260], [-14478, -2532], [-29350, -8480], [-10548, -11172], [-28840, 6740], [-8286, 8976], [13935, 7800], [15421, 3048], [-39920, 9620], [3610, -8960], [-26758, 11348], [-4853, 1236], [-39510, -7740], [-624, 10984], [-11735, -11420], [-11637, -1056], [10122, -9972], [55215, 2580], [-43515, 10520], [-24934, 8600], [19210, 440], [-6590, 12240], [-57890, 4740], [-12810, 4060], [-39765, -1780], [9340, -240], [15760, -10340], [23606, -14072], [-13400, -6900], [-21374, -10156], [-28020, 10720], [3358, 13932], [22365, 13560], [-8610, -5440], [-37060, -7140], [5276, -8676], [-1530, -20], [-6794, -5356], [28652, -712], [-25102, -2776], [21550, -5000], [18151, 16888], [15398, 1712], [-38915, -18080], [23134, -2200], [25075, -9460], [-15081, -13228], [-8925, -9360], [-45888, 6456], [19352, -13572], [-64630, 6080], [-3688, 4400], [60927, 5776], [60695, 9920], [21165, 4120], [24570, 10380], [60252, -1352], [8109, 5692], [-12080, -20420], [49548, 12512], [-62860, -9640], [71095, -2160], [-29266, 15392], [98805, -3780], [1770, -18020], [10280, -16760], [-43530, 13280], [7091, 17300], [-50330, 8420], [85510, -6340], [-45430, 6280], [-62790, -13240], [51180, -10680], [1550, -1840], [-4881, -1500], [-12322, 5464], [-25980, 15000], [-16175, -10060], [44755, -20940], [-41690, -10540], [-97524, 10464], [-63630, -4920], [27835, -5220], [-60690, -10480], [-83920, 2220], [34151, 16688], [44470, 22880], [45018, 19632], [-32298, 23468], [24770, 31980], [-53330, 9420], [-32355, 25380], [16576, 31888], [-46450, -25040], [33095, 7360], [-72144, -3936], [29926, 23400], [35613, 7344], [79670, -16720], [-89475, -4680], [28467, 5100], [103400, -40], [-6420, 18120], [-56245, 12760], [56147, -25364], [-30818, -22332], [-65086, -28484], [38830, 1320], [-9730, -29120], [-66637, -14456], [-102405, 17360], [30282, 17588], [-72930, -3820], [-69478, -8212], [-70850, 19100], [36240, 19560], [33125, 4420], [37240, -39640], [-56125, 22480], [-42295, 6660], [46200, 8600], [20209, -8908], [-8148, -31872], [59783, 404], [4360, -17740], [80946, -19756], [-69300, -25200], [-128044, 13528], [-37870, 30880], [-73860, -2640], [-75231, -13400], [-5602, -24376], [-52270, 14280], [-53546, -27604], [-4160, -7740], [-96570, 4920], [99407, -4700], [-93535, -19260], [19071, 6448], [-120130, 20880], [-5230, 48020], [-39000, -16200], [91298, -9948], [-78918, -5792], [96170, -20520], [-50029, -21452], [-154700, 14160], [85926, 29204], [-27102, 25492], [78838, -10800], [80914, -6244], [-103820, 29720], [26675, -19880], [88348, 29000], [-103515, 5680], [74261, -18632], [139530, 3680], [-33730, 19980], [104615, 6600], [14220, 24120], [-5546, 7336], [102360, 25540], [-51567, 27804], [92148, 9132], [77244, 25672], [76400, -4200], [-85504, 20964], [24360, 19740], [-19365, -47580], [-63850, -50200], [-150776, 3676], [-159633, 10400], [80075, 7560], [141081, 16728], [94350, -27400], [-93450, 400], [140720, -14620], [-106450, -11500], [-96680, 23720], [112844, 2036], [2850, -62800], [94810, 1060], [5999, 13612], [16980, 240], [-159770, 15180], [-26925, -35380], [82982, -21692], [-66103, 45936], [141027, 20676], [-41680, -14420], [-48222, -1568], [-24039, -39400], [-25630, -14120], [-38594, -46416], [-33300, 5400], [209043, -716], [-22185, 8220], [-73920, 29520], [120455, 10420], [-3690, -25960], [103068, -42848], [-26506, -29824], [136404, -35424], [-17570, -52780], [49265, 49640], [-72203, -26164], [15155, 6420], [135568, -21448], [112735, 20440], [-101831, -37728], [104595, -31020], [-55359, 27708], [-520, -9520], [-98817, 3804], [-86912, -15768], [73720, -16020], [-167790, 1540], [-166483, -27900], [144882, -29184], [29720, -32620], [60718, -808], [-43084, -11796], [206135, 15580], [-14100, 42000], [-23510, 47160], [57756, -17976], [-3927, 59800], [-980, 1800], [20760, -2560], [-58495, 35060], [34614, -27544], [-46200, -24900], [-92388, -6744], [119276, -29796], [-145920, 23520], [1291, 28300], [81880, 6360], [-50750, -5320], [-23175, 19040], [5071, -25600], [-116370, -5880], [42930, -65720], [76920, 35880], [47535, 43380], [675, 73620], [62802, 71608], [48694, 31400], [-73790, -7260], [60960, -40260]];
    aps := ConvertToHeckeField(raw_aps);
    chi := MakeCharacter_2205_a_Hecke(Universe(aps));
    return ExtendMultiplicatively(weight, aps, chi);
end function;


// To make the newform (type ModFrm), type "MakeNewformModFrm_2205_4_a_x();".
// 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_2205_4_a_x(:prec:=2)
    chi := MakeCharacter_2205_a();
    f_vec := qexpCoeffs();
    Kf := Universe(f_vec);
    // SetVerbose("ModularForms", true);
    // SetVerbose("ModularSymbols", true);
    S := CuspidalSubspace(ModularForms(chi, 4));
    S := BaseChange(S, Kf);
    maxprec := NextPrime(2999) - 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_2205_4_a_x();".
// 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_2205_4_a_x( : sign := -1)
    R<x> := PolynomialRing(Rationals());
    chi := MakeCharacter_2205_a();
    // SetVerbose("ModularSymbols", true);
    Snew := NewSubspace(CuspidalSubspace(ModularSymbols(chi,4,sign)));
    Vf := Kernel([<2,R![-10, 2, 1]>,<11,R![913, 66, 1]>,<13,R![-4375, 10, 1]>,<17,R![-3175, -70, 1]>],Snew);
    return Vf;
end function;