CSL_error
CSL_GenerateEccSharedKey(CSLOSEccPrivateKey privateKey, 
                         CSLOSEccPublicKey publicKey, 
                         CSLOSEccSharedKey sharedKey, u32 numBytes){
    
    field_2n pvtkey, sharedkey;
    point publickey;
    CSLOSEccSharedKey sharedKeyCopy;
    CSL_error error = CSL_OK;
    
    if(numBytes > sizeof(CSLOSEccSharedKey)){
        return CSL_OVERFLOW;
    }
    poly_elliptic_init_233_bit();
    
    OS2FEP(privateKey, &pvtkey);
    OS2ECP(publicKey, OCTET_STRING_LEN*2, &publickey);
    error = alg_generate_shared_key(&named_point, &named_curve, &publickey, &pvtkey, &sharedkey);
    /* collect the result into output */
#ifdef KDF1
    post_process_key(&sharedkey, sharedKeyCopy);
#else
    FE2OSP(sharedKeyCopy, &sharedkey);
#endif
    /* convert to octet string of desired length */
    memcpy(sharedKey, sharedKeyCopy, numBytes);
    

    return error;
}
CSL_error 
CSL_GenerateEccKeyPair(CSLOSEccPrivateRand rand, 
		       CSLOSEccPrivateKey privateKey,
		       CSLOSEccPublicKey publicKey){
  field_2n pvtkey;
  OS2FEP(rand, &pvtkey);
  memset(privateKey, 0x0, sizeof(CSLOSEccPrivateKey));
  FE2OSP(privateKey, &pvtkey);

  return CSL_GenerateEccPublicKey(privateKey, publicKey);
}
    virtual bool setPublicKey(const Octet & PublicKey)
        {
            if (PublicKey.getDataSize() != ( _Lcm * 2 ))
                return false;

            tOS2FEP<typename EC_Dscr::aECP> OS2FEP;

            _Curve.enter_mod_context(EC_Dscr::aEC::FIELD_CONTEXT);

            _publicKey =
                toProjective(_Curve
                             .create(OS2FEP(ByteSeq(PublicKey.getData(), _Lcm)),
                                     OS2FEP(ByteSeq(PublicKey.getData() + _Lcm, _Lcm))),
                             _PCurve);

            _Curve.leave_mod_context();

            _isPublicKeyLoaded = true;

            setPublicKeyHook();

            return _isPublicKeyLoaded;
        }
CSL_error
CSL_ComputeEccSig(CSLOSDigest digest, 
                  u32 digestSize,
                  CSLOSEccPrivateKey private_key, 
                  CSLOSEccSig sign,
                  CSLOSEccSigRand random_data)
{
    CSL_error ret;
    CSL_error reterr = CSL_OK;

    CSL_ComputeEccSig_big_locals *big_locals;
#ifdef __KERNEL__
    big_locals = kmalloc(sizeof(*big_locals), GFP_KERNEL);
    if (!big_locals)
        return CSL_NO_MEMORY;
#else
    CSL_ComputeEccSig_big_locals _big_locals;
    big_locals = &_big_locals;
#endif

    alg_init_233_bit_ECDSA(&big_locals->base, NUM_BITS);
    OS2FEP(private_key, &big_locals->pvtkey);
    OS2FEP(random_data, &big_locals->random_data_field);
    ret = alg_poly_ECDSA_signature((char *)digest, digestSize, &big_locals->base, &big_locals->pvtkey, &big_locals->signature, &big_locals->random_data_field);
    if (ret == CSL_OK) {
        EC2OSP((point *)&big_locals->signature, sign, OCTET_STRING_LEN*2);
        reterr = CSL_OK;
    }
    else
        reterr = CSL_DIVIDE_BY_ZERO;

#ifdef __KERNEL__
    kfree(big_locals);
#endif

    return reterr;
}
CSL_error
CSL_GenerateEccPublicKey(CSLOSEccPrivateKey privateKey,
                         CSLOSEccPublicKey publicKey){
    field_2n pvtkey;
    point publickey;
    CSL_error error = CSL_OK;
    /* this is needed because the sizes are extended to word size multiples*/
    memset(publicKey, 0x0, sizeof(CSLOSEccPublicKey));
    poly_elliptic_init_233_bit();

    OS2FEP(privateKey, &pvtkey);
    error = alg_generate_public_key(&named_point, &named_curve, &pvtkey, &publickey);
    EC2OSP(&publickey, publicKey, OCTET_STRING_LEN*2);
    return error;
}
CSL_error
CSL_GenerateEccSharedKeyPre(CSLOSEccPrivateKey privateKey, 
                            CSLOSEccExpPublicKey publicKey, 
                            CSLOSEccSharedKey sharedKey, 
                            u32 numBytes){
    field_2n pvtkey, sharedkey;
    CSLOSEccSharedKey sharedKeyCopy;
    CSL_error error = CSL_OK;
    int j;
#ifdef __KERNEL__
    point *precomputedpublickey = kmalloc(sizeof(point) * 16, GFP_KERNEL);
    if (!precomputedpublickey)
        return CSL_NO_MEMORY;
#else
    point precomputedpublickey[16];
#endif
    
    poly_elliptic_init_233_bit();
    OS2FEP(privateKey, &pvtkey);    
    /* convert public key to point variable */
    for(j=0; j< 16; j++){
        OS2ECP((publicKey + (2*OCTET_STRING_LEN*j)), (2*OCTET_STRING_LEN),  &(precomputedpublickey[j]));
    }
    error = alg_generate_shared_key_pre(&named_point, &named_curve, &precomputedpublickey[0], &pvtkey, &sharedkey);
    /* collect the result into output */
#ifdef KDF1
    post_process_key(&sharedkey, sharedKeyCopy);
#else
    FE2OSP(sharedKeyCopy, &sharedkey);
#endif
    /* convert to octet string of desired length */
    memcpy(sharedKey, sharedKeyCopy, numBytes);

#ifdef __KERNEL__
    kfree(precomputedpublickey);
#endif

    return error;
}