As Pieter already described in his answer it is not known why the multiplicative inverse of 2 of the generator point of secp256k1
is such a short (166 bit) number.
But interestingly all prime order koblitz curves of the SEC 2 family (secp160k1
, secp192k1
, secp224k1
, secp256k1
) share this unusual property.
Moreover all these short x-coordinates of these source points share a significant amount of their bits (152 bits for all these x-values are the same):
secp160k1: 0x4_8ce563f89a0ed9414f5aa28ad0d96d6795f9c6_2
secp192k1: 0x554123b7_8ce563f89a0ed9414f5aa28ad0d96d6795f9c6_6
secp224k1: 0x3b7_8ce563f89a0ed9414f5aa28ad0d96d6795f9c6_3
secp256k1: 0x3b7_8ce563f89a0ed9414f5aa28ad0d96d6795f9c6_3
(I inserted the _
to visualize the identical part in the numbers.)
So maybe back in the 90s someone at Certicom hashed something into a 160 bit hash and then decided to replace the first and the last 4 bits per curve (and added a prefix value for 3 of them)?
Who knows? It's an interesting mystery. :)
I can highly recommend this short talk from Nadia Heninger about this topic:
https://www.youtube.com/watch?v=NGLR2N4EK58
Edit:
To verify this yourself in Sage (example for secp192k1
, simply change curve parameters for the other secp...k1 curves):
# define the curve from parameters
sage: prime_p = ZZ('0xfffffffffffffffffffffffffffffffffffffffeffffee37')
sage: a = 0
sage: b = 3
sage: secp192k1 = EllipticCurve( GF(prime_p), [a, b] )
sage: order_n = secp192k1.order() # get order of the curve
# generator point G
sage: G = secp192k1.point(('0xdb4ff10ec057e9ae26b07d0280b7f4341da5d1b1eae06c7d' , '0x9b2f2f6d9c5628a7844163d015be86344082aa88d95e2f9d'))
# multiply with multiplicative inverse of 2:
sage: Point_half_G_mod_n = G * ZZ( 1 / GF(order_n)(2) )
# print coordinates in hex:
sage: 'x: %x, y: %x' %( Point_half_G_mod_n.xy() )
'x: 554123b78ce563f89a0ed9414f5aa28ad0d96d6795f9c66, y: 90755fc93ea4b13027fc6c8f337d92c6d00090fad0e8b2c6'