首页 > 其他分享 >GMSSL2.x编译鸿蒙静态库和动态库及使用

GMSSL2.x编译鸿蒙静态库和动态库及使用

时间:2024-07-22 17:06:45浏览次数:15  
标签:bin llvm 鸿蒙 GMSSL2 库及 export OHOS napi SDK

一、编译环境准备

1.1 开发工具

DevEco-Studio下载

1.2 SDK下载

​ 下载编译第三方库的SDK有两种方式,第一种方式从官方渠道根据电脑系统选择对应的SDK版本,第二种方式通过DevEco-Studio下载SDK。本文只介绍通过DevEco-Studio下载SDK的方式。

  • 安装SDK到本地

Xnip2024-07-22_09-55-12

Xnip2024-07-22_10-13-51 Xnip2024-07-22_10-25-15
  • 根据SDK安装位置获取SDK

Xnip2024-07-22_10-38-51

  • 将SDK复制到GMSSL的同级目录并更名为ohos-sdk

Xnip2024-07-22_16-36-50

二、编译鸿蒙架构

​ 第三方库编译鸿蒙架构有两种方式。一种是使用C/C++原生构建工具configure、makefile编译,一种是使用lycium框架快速交叉编译。本文只详细介绍通过configure、makefile编译的方式。

2.1 原生工具构建

  • 编写编译脚本

    #!/bin/bash
    
    # Define paths and environment variables
    # 获取脚本当前所在路径
    CURRENT_PATH="$( cd "$( dirname "${BASH_SOURCE[0]}" )" && pwd )"
    # 获取GmSSL源码路径
    GMSSL_DIR=$CURRENT_PATH/GmSSL2.5.4
    # 取脚本执行的第一个参数
    OHOS_TARGET_ABI=$1
    # 获取鸿蒙SDK路径
    export OHOS_SDK=$CURRENT_PATH/ohos-sdk
    
    # 编译64位架构
    if [ "$OHOS_TARGET_ABI" == "arm64-v8a" ]
    then
        export AS=${OHOS_SDK}/native/llvm/bin/llvm-as
        export CC=${OHOS_SDK}/native/llvm/bin/aarch64-unknown-linux-ohos-clang
        export CXX=${OHOS_SDK}/native/llvm/bin/aarch64-unknown-linux-ohos-clang++
        export LD=${OHOS_SDK}/native/llvm/bin/ld.lld
        export STRIP=${OHOS_SDK}/native/llvm/bin/llvm-strip
        export RANLIB=${OHOS_SDK}/native/llvm/bin/llvm-ranlib
        export OBJDUMP=${OHOS_SDK}/native/llvm/bin/llvm-objdump
        export OBJCOPY=${OHOS_SDK}/native/llvm/bin/llvm-objcopy
        export NM=${OHOS_SDK}/native/llvm/bin/llvm-nm
        export AR=${OHOS_SDK}/native/llvm/bin/llvm-ar
        export CFLAGS="-DOHOS_NDK -fPIC -D__MUSL__=1"
        export CXXFLAGS="-DOHOS_NDK -fPIC -D__MUSL__=1"
        
        outdir=arm64-v8a
        cd ${GMSSL_DIR}
        ./Configure linux-aarch64
        
    elif [ "$OHOS_TARGET_ABI" == "armeabi-v7a" ]
    then
    #编译32位架构
        export AS=${OHOS_SDK}/native/llvm/bin/llvm-as
        export CC=${OHOS_SDK}/native/llvm/bin/armv7-unknown-linux-ohos-clang
        export CXX=${OHOS_SDK}/native/llvm/bin/armv7-unknown-linux-ohos-clang++
        export LD=${OHOS_SDK}/native/llvm/bin/ld.lld
        export STRIP=${OHOS_SDK}/native/llvm/bin/llvm-strip
        export RANLIB=${OHOS_SDK}/native/llvm/bin/llvm-ranlib
        export OBJDUMP=${OHOS_SDK}/native/llvm/bin/llvm-objdump
        export OBJCOPY=${OHOS_SDK}/native/llvm/bin/llvm-objcopy
        export NM=${OHOS_SDK}/native/llvm/bin/llvm-nm
        export AR=${OHOS_SDK}/native/llvm/bin/llvm-ar
        export CFLAGS="-DOHOS_NDK -fPIC -D__MUSL__=1"
        export CXXFLAGS="-DOHOS_NDK -fPIC -D__MUSL__=1"
    
        outdir=armeabi-v7a
        cd ${GMSSL_DIR}
        ./Configure linux-generic32
        
    elif [ "$OHOS_TARGET_ABI" == "x86_64" ]
    then
    #编译32位架构
        export AS=${OHOS_SDK}/native/llvm/bin/llvm-as
        export CC=${OHOS_SDK}/native/llvm/bin/x86_64-unknown-linux-ohos-clang
        export CXX=${OHOS_SDK}/native/llvm/bin/x86_64-unknown-linux-ohos-clang++
        export LD=${OHOS_SDK}/native/llvm/bin/ld.lld
        export STRIP=${OHOS_SDK}/native/llvm/bin/llvm-strip
        export RANLIB=${OHOS_SDK}/native/llvm/bin/llvm-ranlib
        export OBJDUMP=${OHOS_SDK}/native/llvm/bin/llvm-objdump
        export OBJCOPY=${OHOS_SDK}/native/llvm/bin/llvm-objcopy
        export NM=${OHOS_SDK}/native/llvm/bin/llvm-nm
        export AR=${OHOS_SDK}/native/llvm/bin/llvm-ar
        export CFLAGS="-DOHOS_NDK -fPIC -D__MUSL__=1"
        export CXXFLAGS="-DOHOS_NDK -fPIC -D__MUSL__=1"
    
        outdir=x86_64
        # Navigate to OpenSSL directory
        ./Configure linux-x86_64
        
    else
        echo "Unsupported target ABI: $ANDROID_TARGET_ABI"
        exit 1
    fi
    
    make
    
    # Copy the outputs
    OUTPUT_INCLUDE=$CURRENT_PATH/ohos_libs/include
    OUTPUT_LIB=$CURRENT_PATH/ohos_libs/lib/${outdir}
    mkdir -p $OUTPUT_INCLUDE
    mkdir -p $OUTPUT_LIB
    cp -RL include/openssl $OUTPUT_INCLUDE
    cp libcrypto.so.1.1 $OUTPUT_LIB
    cp libcrypto.a $OUTPUT_LIB
    cp libssl.so.1.1 $OUTPUT_LIB
    cp libssl.a $OUTPUT_LIB
    

    将编写好的脚本文件命名为ohos.sh。文件之间的目录结构如下:

    Xnip2024-07-22_11-23-56

  • 执行脚本

    cd到HarmonyOS-SDK目录下,依次执行如下命令,分别编译64位、32位、x86_64的鸿蒙架构。

    ohos.sh  arm64-v8a
    
    ohos.sh  armeabi-v7a
    
    ohos.sh  x86_64
    
  • 编译问题

    截屏2024-07-19 11.11.09

    解决方案:删除GMSSL2.5.4源码中对getcontext、makecontext、setcontext等函数的引用。

2.2 使用lycium框架编译

三、使用库文件

​ 鸿蒙工程可以使用.a的静态库和.so的动态库,两种类型的库引用一种即可。

3.1 创建NAPI工程

​ NAPI是OpenHarmony系统中的原生模块扩展开发框架,提供JavaScript与C/C++模块之间相互调用的交互能力。

Xnip2024-07-22_14-43-42

  • 添加二进制文件到工程

Xnip2024-07-22_15-03-28

如果该三方库二进制文件为so文件,还需要将so文件拷贝到工程目录的entry/libs/${OHOS_ARCH}/目录下,如下图:

so_location

3.2 配置链接

​ 添加二进制文件后需要在cpp目录的CMakeLists.txt文件中添加对应target_link_libraries才能被工程引用。

  • 配置静态库链接

    target_link_libraries(product PRIVATE ${CMAKE_CURRENT_SOURCE_DIR}/thirdparty/gmssl/${OHOS_ARCH}/lib/libcrypto.a)
    target_link_libraries(product PRIVATE ${CMAKE_CURRENT_SOURCE_DIR}/thirdparty/gmssl/${OHOS_ARCH}/lib/libssl.a)
    
  • 配置动态库链接

    target_link_libraries(product PRIVATE ${CMAKE_CURRENT_SOURCE_DIR}/thirdparty/gmssl/${OHOS_ARCH}/lib/libcrypto.so)
    target_link_libraries(product PRIVATE ${CMAKE_CURRENT_SOURCE_DIR}/thirdparty/gmssl/${OHOS_ARCH}/lib/libssl.so)
    
  • 配置头文件

    target_include_directories(product PRIVATE ${CMAKE_CURRENT_SOURCE_DIR}/thirdparty/gmssl/${OHOS_ARCH}/include)
    

Xnip2024-07-22_15-16-13

四、编写NAPI接口

​ 配置完三方库的链接和头文件路径后,可以根据各自的业务逻辑调用三方库对应的接口完成NAPI接口的编写,NAPI接口开发可以参照以下文档学习。

  1. 使用Node-API实现跨语言交互开发流程

  2. C/C++三方库使用

4.1 NAPI编写示例

​ NAPI接口编写的基本思路是将从JavaScript层传入的参数转成C/C++数据类型,然后调用第三方库接口执行业务逻辑,最后将执行的结果转成JavaScript数据类型返回给JavaScript层。

Xnip2024-07-22_15-43-46

  • 编写接口

    napi_init.cpp文件中编写NAPI接口。

第一步:获取JS层传入的参数转成C/C++数据类型并将转换的结果作为参数传入第三方库函数中。

static napi_value gm_post(napi_env env, napi_callback_info info){
    size_t argc = 4;
    napi_value args[4];
    // 获取JS参数
    napi_get_cb_info(env, info, &argc, args , nullptr, nullptr);
    char url[512] = {0},parameter[MAX_BUF] = {0}, filePath[1024] = {0};
    size_t url_len,parameter_len,filePath_len;
    double timeOut;
    // 获取请求地址 napi(JS)数据类型转c/c++数据类型
    napi_get_value_string_utf8(env, args[0], url, sizeof(url), &url_len);
    // 获取请求参数 napi(JS)数据类型转c/c++数据类型
    napi_get_value_string_utf8(env, args[1], parameter, sizeof(parameter), &parameter_len);
    // 获取超时时间
    napi_get_value_double(env, args[2], &timeOut);
    // 获取证书路径
    napi_get_value_string_utf8(env, args[3], filePath, sizeof(filePath), &filePath_len);
    // 调用gmssl库的post请求方法
    resp_t *resp = infosecPost(url, parameter, timeOut, NULL, filePath);
    // 格式转换后返回响应数据
    return transformRespToNapi(env, resp);
}

第二步:将第三方库返回的结果转成JavaScript数据类型

static napi_value transformRespToNapi(napi_env env,resp_t *resp){
    napi_value res_obj;
    // 1.创建对象
    napi_status status = napi_create_object(env, &res_obj);
    if (status != napi_ok) {
        napi_throw_error(env,"-1","创建响应数据对象异常");
        return nullptr;
    }
    // 2.创建data属性值
    napi_value res_data;
    status = napi_create_string_utf8(env, resp->data, NAPI_AUTO_LENGTH, &res_data);
    if (status != napi_ok) {
        napi_throw_error(env,"-2","创建属性值异常");
        return nullptr;
    }
    status = napi_set_named_property(env, res_obj, "data", res_data);
    if (status != napi_ok) {
        napi_throw_error(env,"-3","设置对象的属性异常");
        return nullptr;
    }
    // 3.创建code属性
    napi_value res_code;
    status = napi_create_double(env, resp->code, &res_code);
     if (status != napi_ok) {
        napi_throw_error(env,"-2","创建属性值异常");
        return nullptr;
    }
    status = napi_set_named_property(env, res_obj, "code", res_code);
    if (status != napi_ok) {
        napi_throw_error(env,"-3","设置对象的属性异常");
        return nullptr;
    }
    resp_free(resp);
    return res_obj;
}

第三步:ArkTS接口与C/C++接口绑定和映射

EXTERN_C_START
static napi_value Init(napi_env env, napi_value exports)
{
    napi_property_descriptor desc[] = {
        { "send_gm_post", nullptr, gm_post, nullptr, nullptr, nullptr, napi_default, nullptr }
    };
    napi_define_properties(env, exports, sizeof(desc) / sizeof(desc[0]), desc);
    return exports;
}
EXTERN_C_END

​ 说明:send_gm_post是ArkTS的函数名,gm_post是C/C++函数名。

  • 声明ArkTS侧的方法

Index.d.ts文件中声明ArkTS侧的方法。

export const send_gm_post: (url: string,parameters:string,timeOut:number,caPath:string) => object;

标签:bin,llvm,鸿蒙,GMSSL2,库及,export,OHOS,napi,SDK
From: https://www.cnblogs.com/yujiabo/p/18316450

相关文章

  • 鸿蒙UI系统组件06——进度条(Progress)
    如果你也对鸿蒙开发感兴趣,加入“Harmony自习室”吧!扫描下面名片,关注公众号。1、概述Progress是进度条显示组件,显示内容通常为某次目标操作的当前进度。2、创建进度条Progress通过调用接口来创建,接口调用形式如下:Progress(options:{value:number,total?:number,type?......
  • 鸿蒙开发 03 封装 @ohos/axios (最新深度封装)
    鸿蒙开发03封装@ohos/axios(最新深度封装)1、安装@ohos/axios2、开始封装2.1新建utils文件夹和api文件夹2.2在utils文件夹里新建http.ts2.3在api文件夹里新建api.ets3、页面调用4、打印结果1、安装@ohos/axiosohpminstall@ohos/axiosTips:按......
  • 鸿蒙系统简洁
    1:手机开放联盟:开放手机联盟,是谷歌牵头,拉拢手机设备商,芯片商,运营商,通信设备商等一大波公司搞的,目的是为了一起联合起来在移动设备领域一起挣钱,最开始是为了对抗如日中天的苹果,谷歌公司(Google)于2007年宣布34家终端和运营企业加入开放手机联盟(OpenHandsetAlliance),将共同开发名......
  • 【转载】浅谈 pb_ds 库及其在OI其他算竞中的应用
    【原链接】这篇太叼了!pb_ds,比STL更强大的模板库。upd.on10.27更新了优先队列的常数分析,增加了“万能头文件”的内容。前言之前看到过一篇关于pb_ds写得很好的文章,但现在找不到了;OI-wiki上的内容的不太完整。那不如自己动手,丰衣足食。当然,pb_ds库中有很多东西算......
  • 贝壳项目,入库及去重
    importtimeimportrequestsfromlxmlimportetreefrom常用功能.mongodb链接importconnect_mongodbuser_value='bk_spider'pwd_value='ke@spider01'mongo_id_value='119.45.40.170'port_value=27017db_value='spider&#......
  • 云计算【第一阶段(30)】部署Yum仓库及NFS共享服务
    一、Yum仓库1.1、Yum仓库概念学习YUM软件仓库,可以完成安装、卸载、自动升级rpm软件包等任务,能够自动查找并解决rpm包之间的依赖关系,而无须管理员逐个、手工地去安装每个rpm包,使管理员在维护大量Linux服务器时更加轻松自如。特别是在拥有大量Linux主机的本地网络中......
  • 【HarmonyOS NEXT】鸿蒙 代码混淆
    代码混淆简介针对工程源码的混淆可以降低工程被破解攻击的风险,缩短代码的类与成员的名称,减小应用的大小。DevEcoStudio提供代码混淆的能力并默认开启,API10及以上版本的Stage模型、编译模式为release时自动进行代码混淆。使用约束仅支持Stage工程编译模式为release模块及......
  • 【HarmonyOS NEXT】鸿蒙解析JSON字符串 ArkTSUtils.ASON
    为支持将JSON字符串解析成共享数据,ArkTS语言基础库新增了ASON工具。ASON支持开发者解析JSON字符串,并生成共享数据进行跨并发域传输,同时ASON也支持将共享数据转换成JSON字符串。ISendabletypeISendable=lang.ISendableISendable是所有Sendable类型(除null和undefined)的父类......
  • 【最新鸿蒙应用开发】——Router页面路由
    Router路由页面路由指的是在应用程序中实现不同页面之间的跳转,以及数据传递。通过Router模块就可以实现这个功能.1.创建页面之前是创建的文件,使用路由的时候需要创建页面,步骤略有不同方法1:直接右键新建Page(常用)方法2:单独添加页面并配置1.1.直接右键新建Page......
  • 【最新鸿蒙应用开发】——Navigation路由管理
    Navigation路由1.引言一多开发的项目适合使用Navigation进行统一的页面路由管理。Navigation还提供统一的标题栏、工具栏、菜单栏,并且自带导航返回功能。另外,Navigation还支持一些Router不支持的功能,比如:自带的路由拦截功能,自带的沉浸式功能等等。效果图预览代码链接:Navi......