Class: OpenSSL::PKey::EC::Point

Inherits:
Object
  • Object
show all
Defined in:
lib/openssl/pkey.rb,
ext/openssl/ossl_pkey_ec.c

Defined Under Namespace

Classes: Error

Instance Method Summary collapse

Constructor Details

#OpenSSL::PKey::EC::Point.new(point) ⇒ Object #OpenSSL::PKey::EC::Point.new(group[, encoded_point]) ⇒ Object

Creates a new instance of OpenSSL::PKey::EC::Point. If the only argument is an instance of EC::Point, a copy is returned. Otherwise, creates a point that belongs to group.

encoded_point is the octet string representation of the point. This must be either a String or an OpenSSL::BN.



1216
1217
1218
1219
1220
1221
1222
1223
1224
1225
1226
1227
1228
1229
1230
1231
1232
1233
1234
1235
1236
1237
1238
1239
1240
1241
1242
1243
1244
1245
1246
1247
1248
1249
1250
1251
1252
1253
1254
1255
1256
1257
1258
1259
1260
1261
1262
1263
# File 'ext/openssl/ossl_pkey_ec.c', line 1216

static VALUE ossl_ec_point_initialize(int argc, VALUE *argv, VALUE self)
{
    EC_POINT *point;
    VALUE group_v, arg2;
    const EC_GROUP *group;

    TypedData_Get_Struct(self, EC_POINT, &ossl_ec_point_type, point);
    if (point)
        rb_raise(eEC_POINT, "EC_POINT already initialized");

    rb_scan_args(argc, argv, "11", &group_v, &arg2);
    if (rb_obj_is_kind_of(group_v, cEC_POINT)) {
        if (argc != 1)
            rb_raise(rb_eArgError, "invalid second argument");
        return ossl_ec_point_initialize_copy(self, group_v);
    }

    GetECGroup(group_v, group);
    if (argc == 1) {
        point = EC_POINT_new(group);
        if (!point)
            ossl_raise(eEC_POINT, "EC_POINT_new");
    }
    else {
        if (rb_obj_is_kind_of(arg2, cBN)) {
            point = EC_POINT_bn2point(group, GetBNPtr(arg2), NULL, ossl_bn_ctx);
            if (!point)
                ossl_raise(eEC_POINT, "EC_POINT_bn2point");
        }
        else {
            StringValue(arg2);
            point = EC_POINT_new(group);
            if (!point)
                ossl_raise(eEC_POINT, "EC_POINT_new");
            if (!EC_POINT_oct2point(group, point,
                                    (unsigned char *)RSTRING_PTR(arg2),
                                    RSTRING_LEN(arg2), ossl_bn_ctx)) {
                EC_POINT_free(point);
                ossl_raise(eEC_POINT, "EC_POINT_oct2point");
            }
        }
    }

    RTYPEDDATA_DATA(self) = point;
    rb_ivar_set(self, id_i_group, group_v);

    return self;
}

Instance Method Details

#add(point) ⇒ Object

Performs elliptic curve point addition.



1461
1462
1463
1464
1465
1466
1467
1468
1469
1470
1471
1472
1473
1474
1475
1476
1477
1478
1479
1480
1481
# File 'ext/openssl/ossl_pkey_ec.c', line 1461

static VALUE ossl_ec_point_add(VALUE self, VALUE other)
{
    EC_POINT *point_self, *point_other, *point_result;
    const EC_GROUP *group;
    VALUE group_v = rb_attr_get(self, id_i_group);
    VALUE result;

    GetECPoint(self, point_self);
    GetECPoint(other, point_other);
    GetECGroup(group_v, group);

    result = rb_obj_alloc(cEC_POINT);
    ossl_ec_point_initialize(1, &group_v, result);
    GetECPoint(result, point_result);

    if (EC_POINT_add(group, point_result, point_self, point_other, ossl_bn_ctx) != 1) {
        ossl_raise(eEC_POINT, "EC_POINT_add");
    }

    return result;
}

#eql?(point2) ⇒ Boolean #==(point2) ⇒ Boolean Also known as: ==



1295
1296
1297
1298
1299
1300
1301
1302
1303
1304
1305
1306
1307
1308
1309
1310
1311
1312
1313
1314
1315
1316
# File 'ext/openssl/ossl_pkey_ec.c', line 1295

static VALUE ossl_ec_point_eql(VALUE a, VALUE b)
{
    EC_POINT *point1, *point2;
    VALUE group_v1 = rb_attr_get(a, id_i_group);
    VALUE group_v2 = rb_attr_get(b, id_i_group);
    const EC_GROUP *group;

    if (ossl_ec_group_eql(group_v1, group_v2) == Qfalse)
        return Qfalse;

    GetECPoint(a, point1);
    GetECPoint(b, point2);
    GetECGroup(group_v1, group);

    switch (EC_POINT_cmp(group, point1, point2, ossl_bn_ctx)) {
      case 0: return Qtrue;
      case 1: return Qfalse;
      default: ossl_raise(eEC_POINT, "EC_POINT_cmp");
    }

    UNREACHABLE;
}

#infinity?Boolean



1322
1323
1324
1325
1326
1327
1328
1329
1330
1331
1332
1333
1334
1335
1336
1337
# File 'ext/openssl/ossl_pkey_ec.c', line 1322

static VALUE ossl_ec_point_is_at_infinity(VALUE self)
{
    EC_POINT *point;
    const EC_GROUP *group;

    GetECPoint(self, point);
    GetECPointGroup(self, group);

    switch (EC_POINT_is_at_infinity(group, point)) {
      case 1: return Qtrue;
      case 0: return Qfalse;
      default: ossl_raise(eEC_POINT, "EC_POINT_is_at_infinity");
    }

    UNREACHABLE;
}

#initialize_copy(other) ⇒ Object

:nodoc:



1266
1267
1268
1269
1270
1271
1272
1273
1274
1275
1276
1277
1278
1279
1280
1281
1282
1283
1284
1285
1286
1287
1288
# File 'ext/openssl/ossl_pkey_ec.c', line 1266

static VALUE
ossl_ec_point_initialize_copy(VALUE self, VALUE other)
{
    EC_POINT *point, *point_new;
    EC_GROUP *group;
    VALUE group_v;

    TypedData_Get_Struct(self, EC_POINT, &ossl_ec_point_type, point_new);
    if (point_new)
        ossl_raise(eEC_POINT, "EC::Point already initialized");
    GetECPoint(other, point);

    group_v = rb_obj_dup(rb_attr_get(other, id_i_group));
    GetECGroup(group_v, group);

    point_new = EC_POINT_dup(point, group);
    if (!point_new)
        ossl_raise(eEC_POINT, "EC_POINT_dup");
    RTYPEDDATA_DATA(self) = point_new;
    rb_ivar_set(self, id_i_group, group_v);

    return self;
}

#invert!self



1387
1388
1389
1390
1391
1392
1393
1394
1395
1396
1397
1398
1399
# File 'ext/openssl/ossl_pkey_ec.c', line 1387

static VALUE ossl_ec_point_invert(VALUE self)
{
    EC_POINT *point;
    const EC_GROUP *group;

    GetECPoint(self, point);
    GetECPointGroup(self, group);

    if (EC_POINT_invert(group, point, ossl_bn_ctx) != 1)
        ossl_raise(eEC_POINT, "EC_POINT_invert");

    return self;
}

#make_affine!self

This method is deprecated and should not be used. This is a no-op.



1366
1367
1368
1369
1370
1371
1372
1373
1374
1375
1376
1377
1378
1379
1380
1381
# File 'ext/openssl/ossl_pkey_ec.c', line 1366

static VALUE ossl_ec_point_make_affine(VALUE self)
{
    EC_POINT *point;
    const EC_GROUP *group;

    GetECPoint(self, point);
    GetECPointGroup(self, group);

    rb_warn("OpenSSL::PKey::EC::Point#make_affine! is deprecated");
#if !defined(OSSL_HAVE_IMMUTABLE_PKEY) && !defined(OPENSSL_IS_AWSLC)
    if (EC_POINT_make_affine(group, point, ossl_bn_ctx) != 1)
        ossl_raise(eEC_POINT, "EC_POINT_make_affine");
#endif

    return self;
}

#mul(bn1[, bn2]) ⇒ Object

Performs elliptic curve point multiplication.

The first form calculates bn1 * point + bn2 * G, where G is the generator of the group of point. bn2 may be omitted, and in that case, the result is just bn1 * point.

Before version 4.0.0, and when compiled with OpenSSL 1.1.1 or older, this method allowed another form:

point.mul(bns, points [, bn2]) => point


1497
1498
1499
1500
1501
1502
1503
1504
1505
1506
1507
1508
1509
1510
1511
1512
1513
1514
1515
1516
1517
1518
1519
1520
1521
1522
1523
1524
# File 'ext/openssl/ossl_pkey_ec.c', line 1497

static VALUE ossl_ec_point_mul(int argc, VALUE *argv, VALUE self)
{
    EC_POINT *point_self, *point_result;
    const EC_GROUP *group;
    VALUE group_v = rb_attr_get(self, id_i_group);
    VALUE arg1, arg2, arg3, result;
    const BIGNUM *bn_g = NULL;

    GetECPoint(self, point_self);
    GetECGroup(group_v, group);

    result = rb_obj_alloc(cEC_POINT);
    ossl_ec_point_initialize(1, &group_v, result);
    GetECPoint(result, point_result);

    rb_scan_args(argc, argv, "12", &arg1, &arg2, &arg3);
    if (RB_TYPE_P(arg1, T_ARRAY) || argc > 2)
        rb_raise(rb_eNotImpError, "OpenSSL::PKey::EC::Point#mul with arrays " \
                 "is no longer supported");

    BIGNUM *bn = GetBNPtr(arg1);
    if (!NIL_P(arg2))
        bn_g = GetBNPtr(arg2);
    if (EC_POINT_mul(group, point_result, bn_g, point_self, bn, ossl_bn_ctx) != 1)
        ossl_raise(eEC_POINT, NULL);

    return result;
}

#on_curve?Boolean



1343
1344
1345
1346
1347
1348
1349
1350
1351
1352
1353
1354
1355
1356
1357
1358
# File 'ext/openssl/ossl_pkey_ec.c', line 1343

static VALUE ossl_ec_point_is_on_curve(VALUE self)
{
    EC_POINT *point;
    const EC_GROUP *group;

    GetECPoint(self, point);
    GetECPointGroup(self, group);

    switch (EC_POINT_is_on_curve(group, point, ossl_bn_ctx)) {
      case 1: return Qtrue;
      case 0: return Qfalse;
      default: ossl_raise(eEC_POINT, "EC_POINT_is_on_curve");
    }

    UNREACHABLE;
}

#set_to_infinity!self



1405
1406
1407
1408
1409
1410
1411
1412
1413
1414
1415
1416
1417
# File 'ext/openssl/ossl_pkey_ec.c', line 1405

static VALUE ossl_ec_point_set_to_infinity(VALUE self)
{
    EC_POINT *point;
    const EC_GROUP *group;

    GetECPoint(self, point);
    GetECPointGroup(self, group);

    if (EC_POINT_set_to_infinity(group, point) != 1)
        ossl_raise(eEC_POINT, "EC_POINT_set_to_infinity");

    return self;
}

#to_bn(conversion_form = group.point_conversion_form) ⇒ Object

:call-seq:

point.to_bn([conversion_form]) -> OpenSSL::BN

Returns the octet string representation of the EC point as an instance of OpenSSL::BN.

If conversion_form is not given, the point_conversion_form attribute set to the group is used.

See #to_octet_string for more information.



330
331
332
# File 'lib/openssl/pkey.rb', line 330

def to_bn(conversion_form = group.point_conversion_form)
  OpenSSL::BN.new(to_octet_string(conversion_form), 2)
end

#to_octet_string(conversion_form) ⇒ String

Returns the octet string representation of the elliptic curve point.

conversion_form specifies how the point is converted. Possible values are:

  • :compressed

  • :uncompressed

  • :hybrid



1431
1432
1433
1434
1435
1436
1437
1438
1439
1440
1441
1442
1443
1444
1445
1446
1447
1448
1449
1450
1451
1452
1453
# File 'ext/openssl/ossl_pkey_ec.c', line 1431

static VALUE
ossl_ec_point_to_octet_string(VALUE self, VALUE conversion_form)
{
    EC_POINT *point;
    const EC_GROUP *group;
    point_conversion_form_t form;
    VALUE str;
    size_t len;

    GetECPoint(self, point);
    GetECPointGroup(self, group);
    form = parse_point_conversion_form_symbol(conversion_form);

    len = EC_POINT_point2oct(group, point, form, NULL, 0, ossl_bn_ctx);
    if (!len)
        ossl_raise(eEC_POINT, "EC_POINT_point2oct");
    str = rb_str_new(NULL, (long)len);
    if (!EC_POINT_point2oct(group, point, form,
                            (unsigned char *)RSTRING_PTR(str), len,
                            ossl_bn_ctx))
        ossl_raise(eEC_POINT, "EC_POINT_point2oct");
    return str;
}