
// Make newform 90.12.c.a in Magma, downloaded from the LMFDB on 08 September 2025.
// To make the character of type GrpDrchElt, type "MakeCharacter_90_c();"
// To make the character of type GrpDrchElt with Codomain the HeckeField, type "MakeCharacter_90_c_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_90_12_c_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_90_12_c_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 := [79524, 0, 565, 0, 1];
        Kf := NumberField(Polynomial([elt : elt in poly]));
        AssignNames(~Kf, ["nu"]);
    end if;
    Rf_num := [[1, 0, 0, 0], [0, -566, 0, -2], [398466, 1693, 1410, 1], [398466, -1693, 1410, -1]];
    Rf_basisdens := [1, 141, 282, 282];
    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_90_c();"
function MakeCharacter_90_c()
    N := 90;
    order := 2;
    char_gens := [11, 37];
    v := [2, 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;

// To make the character of type GrpDrchElt with Codomain the HeckeField, type "MakeCharacter_90_c_Hecke();"
function MakeCharacter_90_c_Hecke( : Kf := false)
    N := 90;
    order := 2;
    char_gens := [11, 37];
    char_values := [[1, 0, 0, 0], [-1, 0, 0, 0]];
    assert UnitGenerators(DirichletGroup(N)) eq char_gens;
    values := ConvertToHeckeField(char_values : pass_field := ISA(Type(Kf), Fld), 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]];
    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 := 12;
    raw_aps := [[0, 8, 0, 0], [0, 0, 0, 0], [-1205, -430, -55, -10], [0, 3450, 23, -23], [112892, 0, 121, 121], [0, -106929, -3519, 3519], [0, -521884, 36729, -36729], [9089472, 0, 5148, 5148], [0, 434629, 124884, -124884], [-63644238, 0, -760617, -760617], [-76514324, 0, 1326006, 1326006], [0, -3985863, -2498263, 2498263], [-219522406, 0, 584914, 584914], [0, -90884901, -6829568, 6829568], [0, -393769937, -667422, 667422], [0, 398856678, -9864603, 9864603], [3890738300, 0, 27147415, 27147415], [-65598982, 0, -24739056, -24739056], [0, 2483331225, -23000342, 23000342], [-114355008, 0, 8776386, 8776386], [0, -2243291304, -95903234, 95903234], [-366791292, 0, -109382778, -109382778], [0, 8906564245, -81373464, 81373464], [17218627270, 0, -438921160, -438921160], [0, -15006292338, -232833128, 232833128], [83095080682, 0, -692239009, -692239009], [0, -3279533676, -6032083, 6032083], [0, 7544755461, -1029292596, 1029292596], [11915195930, 0, -68893470, -68893470], [0, -10154504556, -1416210651, 1416210651], [0, -40192335582, -363410281, 363410281], [678315451308, 0, 896310435, 896310435], [0, -41042476944, -2657767761, 2657767761], [215886972176, 0, 3162017214, 3162017214], [462349993718, 0, -1013998493, -1013998493], [-625759879292, 0, 5437280394, 5437280394], [0, -202014216237, -2090729861, 2090729861], [0, 201319847265, -9685670386, 9685670386], [0, -7424663283, 15528165336, -15528165336], [0, -494415366022, 9696861927, -9696861927], [-1709862359332, 0, 18168310327, 18168310327], [-4455020559250, 0, -140151618, -140151618], [2892851626680, 0, 22481117478, 22481117478], [0, -315710497686, 22912165162, -22912165162], [0, 273887194096, -9994144041, 9994144041], [5757007281060, 0, -5614341210, -5614341210], [-1929611434368, 0, 6011691930, 6011691930], [0, -611180324292, -46229987375, 46229987375], [0, 993069807809, 18579921120, -18579921120], [656971784254, 0, 84280470426, 84280470426], [0, 2618111077064, -48459114081, 48459114081], [13398615170968, 0, -12734755258, -12734755258], [4842396661534, 0, 116351488908, 116351488908], [-10512728402124, 0, -15879917553, -15879917553], [0, 2058471277248, -149968988937, 149968988937], [0, -1733182326587, -43900929468, 43900929468], [31835823071598, 0, -31145203143, -31145203143], [18141102513580, 0, -171637298658, -171637298658], [0, -1234110569037, 44737600709, -44737600709], [-16907497666902, 0, -89856104580, -89856104580], [0, 9628608873693, -89860118170, 89860118170], [0, 71092018812, -127926717255, 127926717255], [0, -17800149330981, -117860663844, 117860663844], [-83081487184392, 0, 49743538230, 49743538230], [0, 21378611720202, 90113107498, -90113107498], [0, 15544546922636, 120389433669, -120389433669], [76583275144456, 0, 59209725276, 59209725276], [0, -24657402524460, 105937422758, -105937422758], [0, 8077508372205, 583112457972, -583112457972], [3847146203414, 0, 258346670436, 258346670436], [0, 9941221014236, 545500761903, -545500761903], [35209836273864, 0, 577652186076, 577652186076], [0, -4750403536446, 336651973511, -336651973511], [0, 14567462539785, 527164898589, -527164898589], [-71777310751544, 0, -290382232626, -290382232626], [0, 20284721688467, -480586734810, 480586734810], [-211252115391242, 0, -407417329273, -407417329273], [0, -30946872899319, 1032779172905, -1032779172905], [242287239156910, 0, 187918038038, 187918038038], [30101231781622, 0, -397912981662, -397912981662], [-171938186729348, 0, -956934443947, -956934443947], [-127032294399758, 0, -878450703570, -878450703570], [140385433280168, 0, -438676206500, -438676206500], [0, 64970460016890, -1588946874566, 1588946874566], [102765183576804, 0, -60723798714, -60723798714], [0, 102728129016945, 609937520076, -609937520076], [-433031357440302, 0, 950694142902, 950694142902], [0, -26394101059758, -3358438828708, 3358438828708], [541654462716498, 0, -1969085394135, -1969085394135], [0, 151861137464106, 344156908251, -344156908251], [0, 77737953386037, -3448405586124, 3448405586124], [-85453185374576, 0, -2381593488454, -2381593488454], [0, -105968274207336, -868958779899, 868958779899], [550228795597212, 0, 463058205771, 463058205771], [-153783220279080, 0, 367324199280, 367324199280], [0, -4787207607705, -3250577162934, 3250577162934], [124127210937954, 0, 3797726912511, 3797726912511], [-104069890545962, 0, 7793765753090, 7793765753090], [0, 158222496298269, 2149883546102, -2149883546102], [570871849882630, 0, 4681429334262, 4681429334262], [0, -6638539509141, 1629607156976, -1629607156976], [0, -192801789653682, 1080512969103, -1080512969103], [0, 484402777211069, 2638400151924, -2638400151924], [42952382803402, 0, -985250691322, -985250691322], [458382333996760, 0, 5474810128212, 5474810128212], [0, 151667415462360, -4301049189712, 4301049189712], [0, -272840728189431, 4340973510180, -4340973510180], [0, 408016406675352, 2088484192125, -2088484192125], [-720999283012680, 0, 1869331213380, 1869331213380], [1395103424250422, 0, 80221740030, 80221740030], [0, -211027766251872, 14812567755169, -14812567755169], [0, 246878559771819, -2580636368333, 2580636368333], [0, -246598139905264, 3123005769369, -3123005769369], [-670782458222480, 0, -16876817583750, -16876817583750], [2040729564516332, 0, -12675212376750, -12675212376750], [-1395926293376206, 0, 11867577150214, 11867577150214], [0, 356082589433601, 19005829498746, -19005829498746], [0, -642342889139361, 6369636646710, -6369636646710], [0, -114497758975640, -13503459910329, 13503459910329], [900339368913284, 0, 6132640128781, 6132640128781], [-522821951449102, 0, 16457611568364, 16457611568364], [0, 800672964642, -21048986164962, 21048986164962], [0, 467406940372892, -25757012746899, 25757012746899], [0, 33230246886625, 13693224937896, -13693224937896], [32749417359712, 0, -21623862768120, -21623862768120], [1302994774909166, 0, -32921739522743, -32921739522743], [4523356940585118, 0, 3516616559142, 3516616559142], [1169067192203224, 0, -40052039136544, -40052039136544], [0, 1025862866709480, -21126453585147, 21126453585147], [0, -362203245320199, 45572985366611, -45572985366611], [2441943418793960, 0, -41090054234220, -41090054234220], [0, 884748370685799, 3603187858554, -3603187858554], [-4071716113728436, 0, -26205079879062, -26205079879062], [0, 376755678097455, 37777798795133, -37777798795133], [10329297218745510, 0, -9347442429522, -9347442429522], [-7619073103677870, 0, 21308731595190, 21308731595190], [0, -246958121167236, -34947403590321, 34947403590321], [0, 946831588574349, 72659095115246, -72659095115246], [0, 88323536778134, -32475263694975, 32475263694975], [-6554175572378634, 0, 30667709074974, 30667709074974], [-11001752845204712, 0, -29124451222326, -29124451222326], [9013371457188550, 0, 64851863919953, 64851863919953], [0, -2824413266372670, 51415768671579, -51415768671579], [0, 2628761559333629, 51882140126160, -51882140126160], [-113057982696054, 0, 52727624500734, 52727624500734], [-7758140879099560, 0, 37873918601320, 37873918601320], [0, -2127566744779821, -77717888656273, 77717888656273], [0, -260740988083236, 63680147896725, -63680147896725], [-2242021187624936, 0, 99804777439446, 99804777439446], [0, -1565860335777003, 48907678192920, -48907678192920], [0, -5093859204127569, 39782264349235, -39782264349235], [-2857283281187262, 0, 32733496471680, 32733496471680], [0, -6038428841316603, 34119749889858, -34119749889858], [0, -265419401815311, -13013154085680, 13013154085680], [0, 1995519525130899, -90756114920484, 90756114920484], [16692429947868912, 0, 6921132788976, 6921132788976], [-8688248167329948, 0, -89937271890882, -89937271890882], [-15622787692902510, 0, 149089225079430, 149089225079430], [0, -585422768261172, -151007784418676, 151007784418676], [-5426377000286494, 0, 86919127101877, 86919127101877], [0, -44856745498755, -67325845892148, 67325845892148], [0, -5521434659162308, 52003426304745, -52003426304745], [0, 550268775207978, 234224735718379, -234224735718379], [19794272252457204, 0, -119203621179201, -119203621179201], [0, 4072828029114636, -52439403415491, 52439403415491], [0, -1591329650330653, -210315525444450, 210315525444450], [24041489501778292, 0, 27695404751850, 27695404751850], [0, 4833752307055263, -49792834246521, 49792834246521]];
    aps := ConvertToHeckeField(raw_aps);
    chi := MakeCharacter_90_c_Hecke( : Kf := Universe(aps));
    return ExtendMultiplicatively(weight, aps, chi);
end function;


// To make the newform (type ModFrm), type "MakeNewformModFrm_90_12_c_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_90_12_c_a(:prec:=4)
    chi := MakeCharacter_90_c();
    f_vec := qexpCoeffs();
    Kf := Universe(f_vec);
    // SetVerbose("ModularForms", true);
    // SetVerbose("ModularSymbols", true);
    S := CuspidalSubspace(ModularForms(chi, 12));
    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_90_12_c_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_90_12_c_a( : sign := -1)
    R<x> := PolynomialRing(Rationals());
    chi := MakeCharacter_90_c();
    // SetVerbose("ModularSymbols", true);
    Snew := NewSubspace(CuspidalSubspace(ModularSymbols(chi,12,sign)));
    Vf := Kernel([<7,R![31477194981714496, 0, 414560372, 0, 1]>],Snew);
    return Vf;
end function;