未完成草稿: strongswan RPM包

yum download --source strongswan

  • diff SPECS/mystrongswan.spec SPECS/strongswan.spec
52d51
< BuildRequires:    tpm2-tss-devel
125c124
<     --enable-tss-tss2 --enable-tpm \
---
>     --with-tss=trousers \
288d286
< %{_libdir}/%{name}/plugins/lib%{name}-tpm.so

strongSwan 与 Openswan 都是 νρΝ 软件

安装主程序包

sudo apt-get install strongswan

安装扩展包, Ubunut 1704中包含支持TPM 2.0的插件

sudo apt-get install libstrongswan-extra-plugins
sudo apt-get install strongswan-pki

--enable-tss-tss2
enable TPM 2.0 TSS2 library, requires libtss2 library [ no ]. Since 5.5.0.

Documents of the usage of pki against tpm handles can be found at:

  • https://wiki.strongswan.org/projects/strongswan/wiki/TpmPlugin

pki命令与TPM2.0相关的插件代码位于
https://github.com/strongswan/strongswan/blob/master/src/libtpmtss/tpm_tss_tss2.c

/**
 * read the public key portion of a TSS 2.0 AIK key from NVRAM
 */
bool read_public(private_tpm_tss_tss2_t *this, TPMI_DH_OBJECT handle,
    TPM2B_PUBLIC *public)
{
    uint32_t rval;

    TPM2B_NAME name = { { sizeof(TPM2B_NAME)-2, } };
    TPM2B_NAME qualified_name = { { sizeof(TPM2B_NAME)-2, } };

    TPMS_AUTH_RESPONSE session_data;
    TSS2_SYS_RSP_AUTHS sessions_data;
    TPMS_AUTH_RESPONSE *session_data_array[1];

    session_data_array[0]  = &session_data;
    sessions_data.rspAuths = &session_data_array[0];
    sessions_data.rspAuthsCount = 1;

    /* read public key for a given object handle from TPM 2.0 NVRAM */
    rval = Tss2_Sys_ReadPublic(this->sys_context, handle, 0, public, &name,
                               &qualified_name, &sessions_data);
    if (rval != TPM_RC_SUCCESS)
    {
        DBG1(DBG_PTS, "%s could not read public key from handle 0x%08x: 0x%06x",
                       LABEL, handle, rval);
        return FALSE;
    }
    return TRUE;
}

typedef chunk_t (*get_public_func_t)(tpm_tss_t *this, uint32_t handle);

static chunk_t _get_public(private_tpm_tss_tss2_t *this, uint32_t handle)
{
    TPM2B_PUBLIC public = { { 0, } };
    TPM_ALG_ID sig_alg, digest_alg;
    chunk_t aik_blob, aik_pubkey = chunk_empty;

    if (!read_public(this, handle, &public))
    {
        return chunk_empty;
    }

    aik_blob = chunk_create((u_char*)&public, sizeof(public));
    DBG3(DBG_LIB, "%s AIK public key blob: %B", LABEL, &aik_blob);

    /* convert TSS 2.0 AIK public key blot into PKCS#1 format */
    switch (public.t.publicArea.type)
    {
        case TPM_ALG_RSA:
        {
            TPM2B_PUBLIC_KEY_RSA *rsa;
            TPMT_RSA_SCHEME *scheme;
            chunk_t aik_exponent, aik_modulus;

            scheme = &public.t.publicArea.parameters.rsaDetail.scheme;
            sig_alg   = scheme->scheme;
            digest_alg = scheme->details.anySig.hashAlg;

            rsa = &public.t.publicArea.unique.rsa;
            aik_modulus = chunk_create(rsa->t.buffer, rsa->t.size);
            aik_exponent = chunk_from_chars(0x01, 0x00, 0x01);

            /* subjectPublicKeyInfo encoding of AIK RSA key */
            if (!lib->encoding->encode(lib->encoding, PUBKEY_SPKI_ASN1_DER,
                    NULL, &aik_pubkey, CRED_PART_RSA_MODULUS, aik_modulus,
                    CRED_PART_RSA_PUB_EXP, aik_exponent, CRED_PART_END))
            {
                DBG1(DBG_PTS, "%s subjectPublicKeyInfo encoding of AIK key "
                              "failed", LABEL);
            }
            break;
        }
        case TPM_ALG_ECC:
        {
            TPMS_ECC_POINT *ecc;
            TPMT_ECC_SCHEME *scheme;
            chunk_t ecc_point;
            uint8_t *pos;

            scheme = &public.t.publicArea.parameters.eccDetail.scheme;
            sig_alg   = scheme->scheme;
            digest_alg = scheme->details.anySig.hashAlg;

            ecc = &public.t.publicArea.unique.ecc;

            /* allocate space for bit string */
            pos = asn1_build_object(&ecc_point, ASN1_BIT_STRING,
                                    2 + ecc->x.t.size + ecc->y.t.size);
            /* bit string length is a multiple of octets */
            *pos++ = 0x00;
            /* uncompressed ECC point format */
            *pos++ = 0x04;
            /* copy x coordinate of ECC point */
            memcpy(pos, ecc->x.t.buffer, ecc->x.t.size);
            pos += ecc->x.t.size;
            /* copy y coordinate of ECC point */
            memcpy(pos, ecc->y.t.buffer, ecc->y.t.size);
            /* subjectPublicKeyInfo encoding of AIK ECC key */
            aik_pubkey = asn1_wrap(ASN1_SEQUENCE, "mm",
                            asn1_wrap(ASN1_SEQUENCE, "mm",
                                asn1_build_known_oid(OID_EC_PUBLICKEY),
                                asn1_build_known_oid(ecc->x.t.size == 32 ?
                                        OID_PRIME256V1 : OID_SECT384R1)),
                            ecc_point);
            break;
        }
        default:
            DBG1(DBG_PTS, "%s unsupported AIK key type", LABEL);
            return chunk_empty;
    }
    DBG1(DBG_PTS, "AIK signature algorithm is %N with %N hash",
         tpm_alg_id_names, sig_alg, tpm_alg_id_names, digest_alg);
    return aik_pubkey;
}

extern get_public_func_t get_public = (get_public_func_t) _get_public;

你可能感兴趣的:(未完成草稿: strongswan RPM包)