BLS abbreviation stands for names of inventors of the scheme, ie., Boneh-Lynn-Shacham, that proposed the scheme in the Short signatures from the Weil pairing paper. The scheme works for pairings-friendly elliptic curves within which two groups are chosen, G1 and G2, with generators g1 and g2, respectively. The secret key sk is then randomly picked between 1 and order(G1). The corresponding public key is
Having hashing function,
Given a pairing, e, verification is checking the equality
Please notice that in any pairing we have elements of two groups, G1 and G2. And due to bilinearity property of the pairing we the following holding
The choices of representation of the different entities are not random and done by purpose. G2 is defined over the quadratic extention of the field and hence the storage demands are larger for G2. The arithmetic requirements are harsher for G2 in comparison with G1. If we are to store all public keys in application then it would be tempting to represent them in G1. If we are to store signatures then it is advantageous to stick to the scheme proposed above. Especially, if public keys could be aggregated. Another performance dimension to ponder is verification, as normally pairing operation is costly. Especially if we compare it to other elliptic curve signature schemes like Schnorr or EdDSA. However, as BLS allows for signature aggregation, not so straightforward in other schemes mentioned, the comparison picture changes dramatically in favor of BLS, especially for multi-signature cases.
Although the same abbreviation, BLS here, stands for Barreto-Lynn-Scott. The family of curves was introduced in this seminal paper. BLS12-381 curve was proposed by Sean Bowe in the context of ZCash. The usage of this curve was adopted in number of other blockchains, like Ethereum 2.0, Skale, Algorand, Dfinity or Chia. There is also support of this curve in Cardano, see for example, cardano-crypto-class and the curve is exposed also in aiken from 3.0 release. The great introduction and motivation for this curve was written in the blog post BLS12-381 For The Rest Of Us. It is especially worth mentioning and repeating that the elliptic curve BLS12-381 is currently in IETF draft revision 12 stage of ratification.
The golden are generated using SageMath.
In order to run it do the following: Download the latest image from docker hub and run the image in Linux CLI
$ docker image pull sagemath/sagemath:latest
$ docker run -it sagemath/sagemath:latest
┌────────────────────────────────────────────────────────────────────┐
│ SageMath version 10.6, Release Date: 2025-03-31 │
│ Using Python 3.12.5. Type "help()" for help. │
└────────────────────────────────────────────────────────────────────┘
sage: ZZ(1234)
1234
sage: ZZ.random_element(10**10)
4134169080
sage: quitDefinition of the `g1` and `g2` generators of BLS12-381 are as follows
$ docker run -it sagemath/sagemath:latest
┌────────────────────────────────────────────────────────────────────┐
│ SageMath version 10.6, Release Date: 2025-03-31 │
│ Using Python 3.12.5. Type "help()" for help. │
└────────────────────────────────────────────────────────────────────┘
sage: # parameters for BLS12-381
sage: z = -0xd201000000010000
sage: q = (z^4 - z^2 + 1)
sage: p = ZZ( z + q*(z - 1)^2/3 )
sage: h1 = ZZ( (z - 1)^2 / 3 )
sage: h2 = ZZ( (z^8 - 4*z^7 + 5*z^6 - 4*z^4 + 6*z^3 - 4*z^2-4*z + 13) / 9 )
sage:
sage: F = GF(p)
sage: F12.<T> = GF(p^12)
sage: RF.<T> = PolynomialRing(F12)
sage: j = (T^2 + 1).roots(ring=F12, multiplicities=0)[0]
sage:
sage: E0 = EllipticCurve(F , [0, 4])
sage: E1 = EllipticCurve(F12, [0, 4])
sage: E2 = EllipticCurve(F12, [0, 4 + 4*j])
sage:
sage: # Generators of G1 and G2 (from https://aandds.com/blog/bls.html)
sage: x1 = 0x17f1d3a73197d7942695638c4fa9ac0fc3688c4f9774b905a14e3a3f171bac586c55e83ff97a1aeffb3af00adb22c6bb
sage: y1 = 0x08b3f481e3aaa0f1a09e30ed741d8ae4fcf5e095d5d00af600db18cb2c04b3edd03cc744a2888ae40caa232946c5e7e1
sage: g1 = E1( (x1, y1) )
sage: g1
(3685416753713387016781088315183077757961620795782546409894578378688607592378376318836054947676345821548104185464507 : 1339506544944476473020471379941921221584933875938349620426543736416511423956333506472724655353366534992391756441569 : 1)
sage:
sage: x2 = ( 0x024AA2B2F08F0A91260805272DC51051C6E47AD4FA403B02B4510B647AE3D1770BAC0326A805BBEFD48056C8C121BDB8
....: + 0x13E02B6052719F607DACD3A088274F65596BD0D09920B61AB5DA61BBDC7F5049334CF11213945D57E5AC7D055D042B7E * j )
sage: y2 = ( 0x0CE5D527727D6E118CC9CDC6DA2E351AADFD9BAA8CBDD3A76D429A695160D12C923AC9CC3BACA289E193548608B82801
....: + 0x0606C4A02EA734CC32ACD2B02BC28B99CB3E287E85A763AF267492AB572E99AB3F370D275CEC1DA1AAA9075FF05F79BE * j )
sage: g2 = E2( (x2, y2) )
sage: g2
(1524974934786634869148131047310421674182836367449173499629923666942270478173692664531820817762762612344409858914964*T^11 + 466951167399357819139631101904986341224981495609714517635702448944519312260109086445781162685798203428334155880880*T^10 + 1944629476307696029264710266106104663569401282758349834035384266803502880053233596923517745604293008606776526438813*T^9 + 1064375233906181771446477941731343550152603669242299152704511736901490138163467666912330935749112285497156761812752*T^8 + 524439736117802807566493065558956839033117050732954679474969089293280892348176067052922254028348973140488064346680*T^7 + 139299954118351620793346869471477340669710886265406598127176113079273670344633842262233554267773747834887844661959*T^6 + 739103731826146034717518476459285826868296267538760008155772915279505351525517068683802447801310475600017832001536*T^5 + 896579657303157448006189552190113634690581086624769337632713495534809460193116759284265739854449610289932037083511*T^4 + 843441423355824479944600244225871554713741591724364436154026866899150457470952385866750976645325703303081742979949*T^3 + 1795103225418651429974471490460265646267542049407206684864372758871936629575790147152120418625946616733733618740492*T^2 + 2270793357157838349634671710596689517815160546326318444928655212579690005846921471457165730885514293745964204026559*T + 813014002142981337674656983069970178581719823359786819712640294232766489286415435462948748861707183513679546469441 : 2233067595893406183140797165166489187100525817059352259655242619220390811216367457646110522297226695114452618126428*T^11 + 3602614435636483318959443118205040525998181781525417444771234468139389445877844421472824706983321089450546400870408*T^10 + 3224615712555652661084560310165376476019389757955167724510331501326401626808233747552484652698863330443680962820917*T^9 + 3040382335659451540384754154091661048671599534370655708704703502867830592626379244694086346412062450671231887885165*T^8 + 1459659623750766938694911649253051666276457273093410738960223584589040835447263007618656734237877869272906176926781*T^7 + 525539455293034032098934334132168443354191087251408822811190076148987847200277414420473133234996624365757081282351*T^6 + 1935177694213014925357296420933743720542489252007361846327337055240415803856062332714083431876300729313471329470580*T^5 + 2883239579362127280123556510406854355370944137906162523152958865339387964290988651876855569182930991824507652232201*T^4 + 3942619066893923403018401938436688648248629145749936849043252750084173495049199745561763979760261815776889173528081*T^3 + 1562914866630349508139782242415445213834899573426278635127828361112177413806119582983372787156016586380048149693338*T^2 + 3946024511249678960209495574926206734629277115261246062005271561516945960048572293854026584408693323374250148250856*T + 1779832377062937975389417919695747609689924901440156773060063840000543320473223795889149116063583645025352965406497 : 1)
sage:
sage: iso = E2.isomorphism_to(E1)
sage: k = 12
sage: t = p + 1 - E0.order()
sage:
sage: # points to multiply
sage: p1 = 3 * g1
sage: p2 = 7 * g2
sage:
sage: pairing = p1.ate_pairing(iso(p2), q, k, t, p)
sage: pairing
1387761180978465257476112114847050954511272727021099751707596163090778868843287264887355898156219205646615919788244*T^11 + 1446883575202745040098524998028928188805352441437568605052309003251474833797606339941486005555318295253400449574856*T^10 + 2289356806038184996098713895627084599608283630602663106285535398352867141005601228479347752163145019775636427532012*T^9 + 2487614079649481926416133165448060373372038984938567333577088685317194994073514077232317052321035343791904288247011*T^8 + 3891489328650613869705581914768326688234963543838784031259079251868391300774640519753311173801252953172526822462240*T^7 + 2792435783690433507322189459793051724616954530788354556430819738993112816271592147652996357392630213749489308344656*T^6 + 35111015063507576537592258024431898995755574791121590952023315776751558722050703078334586598819155440635689457708*T^5 + 3783727747182150558562944473240659236675859510095494968580243950919574561954505301371192111500101903932407599056565*T^4 + 873402532902248026825383537764981810447641615734420576800986113571738141480823045073770061259201908983957151880729*T^3 + 2430362863288168000692601594281896253332164292488455504070262876362492167147322899004470395947057992498301611345961*T^2 + 2516516254775662282437328395604952307303479769942541843868334037694383243351020382033415642349702330543329895558588*T + 77785235024769787806807078473160298793133394833594108256424752936500989374455064079184800642853717318883162085283
The proof the above setup is correct is here
COMING SOON
The basic scheme sketched in the introduction is below
COMING SOON