一、 介紹
三方庫指其他公司或者組織提供的服務或者模塊,例如常見的開源 OpenCV 庫,能持續繁榮 OpenAtom OpenHarmony(簡稱“OpenHarmony”)的生態建設。本文介紹如何在 RK3568 開發板上成功移植 OpenJPEG 開源庫。OpenJPEG 是一個用 C 語言編寫的開源 jpeg 2000 編解碼器,可以對圖片進行深度壓縮和解壓等。下面以 OpenJPEG 為例,總結移植三方庫到 OpenHarmony 的經驗。二、開發步驟
三方庫主要是基于標準 Linux 系統的 c/c++ 開源庫,所以三方庫的移植工作,首先是在標準 Linux 系統搭建環境、編譯與驗證,然后將三方庫的編譯加入到 OpenHarmony 工程的構建中。
三方庫移植的主要開發步驟如下:
1.在標準Linux系統下載三方庫源碼,搭建開發環境,編譯整個源碼工程;
2.分析在標準Linux系統的編譯過程文件,提取編譯需要的源文件、編譯依賴等信息;
3.根據上一步分析結果,編寫gn文件,將三方庫加入到OpenHarmony的編譯體系;
4.驗證編譯結果,在OpenHarmony的out目錄是否生成目標庫;
5.測試demo/測試單元用例執行。
注:標準系統編譯構方法可參考 標準系統編譯構建指導
https://gitee.com/openharmony/docs/blob/master/zh-cn/device-dev/subsystems/subsys-build-standard-large.md
三、開源庫的下載與編譯
下面以 OpenJPEG 開源庫為例,詳細的介紹開發流程。
1.搜索OpenJPEG開源庫
本示例的代碼庫鏈接地址:https://github.com/uclouvain/openjpeg

2.下載代碼
在 OpenHarmony/third_party 目錄下,輸入以下命令克隆 OpenJPEG 的源代碼:
git clone git@github.com:uclouvain/openjpeg.git
然后切換到 openjpeg-2.1 分支:
git checkout -b openjp-2.1
3. 執行編譯
代碼倉庫的 INSTALL.md 中詳細介紹了使用 CMake 編譯 OpenJPEG 庫的步驟。本文參考該文檔編譯了 OpenJPEG 庫。若在移植過程中對該庫的編譯選項有疑惑的地方,可參考該文檔。INSTALL 文檔中詳細的介紹了編譯步驟,如下圖:

可以按以上信息,根據如下步驟編譯 openjpeg 工程,具體如下:
在 openjpeg 的目錄下,按以下步驟編譯:
mkdir buildcd buildcmake .. -DCMAKE_BUILD_TYPE=Releasemake
4. 編譯過程
整個編譯過程如下:
water@ubuntu:~/openjpeg/openjpeg/build$ make[] Building C object src/lib/openjp2/CMakeFiles/openjp2_static.dir/thread.c.o[] Building C object src/lib/openjp2/CMakeFiles/openjp2_static.dir/bio.c.o[] Building C object src/lib/openjp2/CMakeFiles/openjp2_static.dir/cio.c.o[] Building C object src/lib/openjp2/CMakeFiles/openjp2_static.dir/dwt.c.o[] Building C object src/lib/openjp2/CMakeFiles/openjp2_static.dir/event.c.o[] Building C object src/lib/openjp2/CMakeFiles/openjp2_static.dir/ht_dec.c.o[] Building C object src/lib/openjp2/CMakeFiles/openjp2_static.dir/image.c.o[] Building C object src/lib/openjp2/CMakeFiles/openjp2_static.dir/invert.c.o[] Building C object src/lib/openjp2/CMakeFiles/openjp2_static.dir/j2k.c.o[] Building C object src/lib/openjp2/CMakeFiles/openjp2_static.dir/jp2.c.o[] Building C object src/lib/openjp2/CMakeFiles/openjp2_static.dir/mct.c.o[] Building C object src/lib/openjp2/CMakeFiles/openjp2_static.dir/mqc.c.o[] Building C object src/lib/openjp2/CMakeFiles/openjp2_static.dir/openjpeg.c.o[] Building C object src/lib/openjp2/CMakeFiles/openjp2_static.dir/opj_clock.c.o[] Building C object src/lib/openjp2/CMakeFiles/openjp2_static.dir/pi.c.o[] Building C object src/lib/openjp2/CMakeFiles/openjp2_static.dir/t1.c.o[] Building C object src/lib/openjp2/CMakeFiles/openjp2_static.dir/t2.c.o[] Building C object src/lib/openjp2/CMakeFiles/openjp2_static.dir/tcd.c.o[] Building C object src/lib/openjp2/CMakeFiles/openjp2_static.dir/tgt.c.o[] Building C object src/lib/openjp2/CMakeFiles/openjp2_static.dir/function_list.c.o[] Building C object src/lib/openjp2/CMakeFiles/openjp2_static.dir/opj_malloc.c.o[] Building C object src/lib/openjp2/CMakeFiles/openjp2_static.dir/sparse_array.c.o[] Linking C static library ../../../bin/libopenjp2.a[] Built target openjp2_static[] Building C object src/lib/openjp2/CMakeFiles/openjp2.dir/thread.c.o[] Building C object src/lib/openjp2/CMakeFiles/openjp2.dir/bio.c.o[] Building C object src/lib/openjp2/CMakeFiles/openjp2.dir/cio.c.o[] Building C object src/lib/openjp2/CMakeFiles/openjp2.dir/dwt.c.o[] Building C object src/lib/openjp2/CMakeFiles/openjp2.dir/event.c.o[] Building C object src/lib/openjp2/CMakeFiles/openjp2.dir/ht_dec.c.o[] Building C object src/lib/openjp2/CMakeFiles/openjp2.dir/image.c.o[] Building C object src/lib/openjp2/CMakeFiles/openjp2.dir/invert.c.o[] Building C object src/lib/openjp2/CMakeFiles/openjp2.dir/j2k.c.o[] Building C object src/lib/openjp2/CMakeFiles/openjp2.dir/jp2.c.o[] Building C object src/lib/openjp2/CMakeFiles/openjp2.dir/mct.c.o[] Building C object src/lib/openjp2/CMakeFiles/openjp2.dir/mqc.c.o[] Building C object src/lib/openjp2/CMakeFiles/openjp2.dir/openjpeg.c.o[] Building C object src/lib/openjp2/CMakeFiles/openjp2.dir/opj_clock.c.o[] Building C object src/lib/openjp2/CMakeFiles/openjp2.dir/pi.c.o[] Building C object src/lib/openjp2/CMakeFiles/openjp2.dir/t1.c.o[] Building C object src/lib/openjp2/CMakeFiles/openjp2.dir/t2.c.o[] Building C object src/lib/openjp2/CMakeFiles/openjp2.dir/tcd.c.o[] Building C object src/lib/openjp2/CMakeFiles/openjp2.dir/tgt.c.o[] Building C object src/lib/openjp2/CMakeFiles/openjp2.dir/function_list.c.o[] Building C object src/lib/openjp2/CMakeFiles/openjp2.dir/opj_malloc.c.o[] Building C object src/lib/openjp2/CMakeFiles/openjp2.dir/sparse_array.c.o[] Linking C shared library ../../../bin/libopenjp2.so[] Built target openjp2[] Building C object src/bin/jp2/CMakeFiles/opj_dump.dir/opj_dump.c.o[] Building C object src/bin/jp2/CMakeFiles/opj_dump.dir/convert.c.o[] Building C object src/bin/jp2/CMakeFiles/opj_dump.dir/convertbmp.c.o[] Building C object src/bin/jp2/CMakeFiles/opj_dump.dir/index.c.o[] Building C object src/bin/jp2/CMakeFiles/opj_dump.dir/__/common/color.c.o[] Building C object src/bin/jp2/CMakeFiles/opj_dump.dir/__/common/opj_getopt.c.o[] Linking C executable ../../../bin/opj_dump[] Built target opj_dump[] Building C object src/bin/jp2/CMakeFiles/opj_compress.dir/opj_compress.c.o[] Building C object src/bin/jp2/CMakeFiles/opj_compress.dir/convert.c.o[] Building C object src/bin/jp2/CMakeFiles/opj_compress.dir/convertbmp.c.o[] Building C object src/bin/jp2/CMakeFiles/opj_compress.dir/index.c.o[] Building C object src/bin/jp2/CMakeFiles/opj_compress.dir/__/common/color.c.o[] Building C object src/bin/jp2/CMakeFiles/opj_compress.dir/__/common/opj_getopt.c.o[] Linking C executable ../../../bin/opj_compress[] Built target opj_compress[] Building C object src/bin/jp2/CMakeFiles/opj_decompress.dir/opj_decompress.c.o[] Building C object src/bin/jp2/CMakeFiles/opj_decompress.dir/convert.c.o[] Building C object src/bin/jp2/CMakeFiles/opj_decompress.dir/convertbmp.c.o[] Building C object src/bin/jp2/CMakeFiles/opj_decompress.dir/index.c.o[] Building C object src/bin/jp2/CMakeFiles/opj_decompress.dir/__/common/color.c.o[] Building C object src/bin/jp2/CMakeFiles/opj_decompress.dir/__/common/opj_getopt.c.o[] Linking C executable ../../../bin/opj_decompress[]Builttargetopj_decompress
依據上述信息中生成 openjp2 庫(libopenjp2.so)的過程可以知道編譯庫需要的 C 源文件,具體內如下所示:
[] Building C object src/lib/openjp2/CMakeFiles/openjp2.dir/thread.c.o[] Building C object src/lib/openjp2/CMakeFiles/openjp2.dir/bio.c.o[] Building C object src/lib/openjp2/CMakeFiles/openjp2.dir/cio.c.o[] Building C object src/lib/openjp2/CMakeFiles/openjp2.dir/dwt.c.o[] Building C object src/lib/openjp2/CMakeFiles/openjp2.dir/event.c.o[] Building C object src/lib/openjp2/CMakeFiles/openjp2.dir/ht_dec.c.o[] Building C object src/lib/openjp2/CMakeFiles/openjp2.dir/image.c.o[] Building C object src/lib/openjp2/CMakeFiles/openjp2.dir/invert.c.o[] Building C object src/lib/openjp2/CMakeFiles/openjp2.dir/j2k.c.o[] Building C object src/lib/openjp2/CMakeFiles/openjp2.dir/jp2.c.o[] Building C object src/lib/openjp2/CMakeFiles/openjp2.dir/mct.c.o[] Building C object src/lib/openjp2/CMakeFiles/openjp2.dir/mqc.c.o[] Building C object src/lib/openjp2/CMakeFiles/openjp2.dir/openjpeg.c.o[] Building C object src/lib/openjp2/CMakeFiles/openjp2.dir/opj_clock.c.o[] Building C object src/lib/openjp2/CMakeFiles/openjp2.dir/pi.c.o[] Building C object src/lib/openjp2/CMakeFiles/openjp2.dir/t1.c.o[] Building C object src/lib/openjp2/CMakeFiles/openjp2.dir/t2.c.o[] Building C object src/lib/openjp2/CMakeFiles/openjp2.dir/tcd.c.o[] Building C object src/lib/openjp2/CMakeFiles/openjp2.dir/tgt.c.o[] Building C object src/lib/openjp2/CMakeFiles/openjp2.dir/function_list.c.o[] Building C object src/lib/openjp2/CMakeFiles/openjp2.dir/opj_malloc.c.o[] Building C object src/lib/openjp2/CMakeFiles/openjp2.dir/sparse_array.c.o[] Linking C shared library ../../../bin/libopenjp2.so[]Builttargetopenjp2
有了以上信息我們可以在后續分析的編譯文件中對比驗證,編譯庫需要的源文件。
5. 查看結果
整個的 build 目錄結構如下:
water@ubuntu:~/openjpeg/openjpeg/build$ tree -L 2.├── bin│ ├── libopenjp2.a│ ├── libopenjp2.so -> libopenjp2.so.7│ ├── libopenjp2.so.2.5.0│ ├── libopenjp2.so.7 -> libopenjp2.so.2.5.0│ ├── opj_compress│ ├── opj_decompress│ └── opj_dump├── CMakeCache.txt├── CMakeFiles│ ├── 3.16.3│ ├── CheckIncludeFiles│ ├── CheckTypeSize│ ├── cmake.check_cache│ ├── CMakeDirectoryInformation.cmake│ ├── CMakeError.log│ ├── CMakeOutput.log│ ├── CMakeTmp│ ├── Export│ ├── Makefile2│ ├── Makefile.cmake│ ├── progress.marks│ ├── TargetDirectories.txt│ ├── TestEndianess.bin│ └── TestLargeFiles.c├── cmake_install.cmake├── CPackConfig.cmake├── CPackSourceConfig.cmake├── CTestCustom.cmake├── libopenjp2.pc├── LICENSE.txt├── Makefile├── OpenJPEGConfig.cmake├── src│ ├── bin│ └── lib├── thirdparty│ ├── CMakeFiles│ ├── cmake_install.cmake│ └── Makefile└── wrapping├── CMakeFiles├── cmake_install.cmake└──Makefile
四、 分析編譯過程
1. 查看生成的庫
首先在 openjpeg/build/bin 目錄可以看出我們需要編譯生成的目標文件,分別為 libopenjp2.a、libopenjp2.so.2.5.0、opj_compress、opj_decompress、opj_dump,還有一些鏈接符號,經過閱讀代碼發現 opj_compress、opj_decompress 和 opj_dump 為一些測試相關的文件,因此可以不加入到代碼工程。

2. 分析生成過程
從 build 目錄下的 Makefile 開始分析生成 libopenjp2.so 所依賴的 C 源文件、cflag 標志、需要包含的頭文件和需要鏈接的庫等信息。
在 openjpeg/build/Makefile 中,可以找到如下信息:
#=============================================================================# Target rules for targets named openjp2# Build rule for target.openjp2: cmake_check_build_system$(MAKE) -f CMakeFiles/Makefile2 openjp2.PHONY : openjp2# fast build rule for target.openjp2/fast:$(MAKE) -f src/lib/openjp2/CMakeFiles/openjp2.dir/build.make src/lib/openjp2/CMakeFiles/openjp2.dir/build.PHONY:openjp2/fast
由上述信息可以發現生成 openjp2 目標是依賴 CMakeFiles/Makefile2 文件。
因此再分析 openjpeg/build/CMakeFiles/Makefile2 這個文件,具體內如下:
src/lib/openjp2/CMakeFiles/openjp2.dir/all:$(MAKE) -f src/lib/openjp2/CMakeFiles/openjp2.dir/build.make src/lib/openjp2/CMakeFiles/openjp2.dir/depend$(MAKE) -f src/lib/openjp2/CMakeFiles/openjp2.dir/build.make src/lib/openjp2/CMakeFiles/openjp2.dir/build@$(CMAKE_COMMAND) -E cmake_echo_color --switch=$(COLOR) --progress-dir=/home/water/openjpeg/openjpeg/build/CMakeFiles --progress-num=1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20,21,22,23 "Built target openjp2".PHONY : src/lib/openjp2/CMakeFiles/openjp2.dir/allsrc/lib/openjp2/CMakeFiles/openjp2.dir/rule: cmake_check_build_system$(CMAKE_COMMAND) -E cmake_progress_start /home/water/openjpeg/openjpeg/build/CMakeFiles 23$(MAKE) -f CMakeFiles/Makefile2 src/lib/openjp2/CMakeFiles/openjp2.dir/all$(CMAKE_COMMAND) -E cmake_progress_start /home/water/openjpeg/openjpeg/build/CMakeFiles 0.PHONY : src/lib/openjp2/CMakeFiles/openjp2.dir/ruleopenjp2: src/lib/openjp2/CMakeFiles/openjp2.dir/rule.PHONY : openjp2src/lib/openjp2/CMakeFiles/openjp2.dir/clean:$(MAKE) -f src/lib/openjp2/CMakeFiles/openjp2.dir/build.make src/lib/openjp2/CMakeFiles/openjp2.dir/clean.PHONY : src/lib/openjp2/CMakeFiles/openjp2.dir/clean
由以上內容可以發現最終是根據 src/lib/openjp2/CMakeFiles/openjp2.dir/build.make 來編譯生成 openjp2 庫。
因此需要再分析 openjpeg/build/src/lib/openjp2/CMakeFiles/openjp2.dir/build.mak。
build.make 文件節選:
//包含depend.make文件include src/lib/openjp2/CMakeFiles/openjp2.dir/depend.make//包含flags.make文件,C_FLAG相關信息include src/lib/openjp2/CMakeFiles/openjp2.dir/flags.make//依賴link.txt,鏈接相關信息cd /home/water/openharmony/third_party/openjpeg/build/src/lib/openjp2 && $(CMAKE_COMMAND) -E cmake_link_script CMakeFiles/openjp2.dir/link.txt --verbose=$(VERBOSE)cd /home/water/openharmony/third_party/openjpeg/build/src/lib/openjp2 && $(CMAKE_COMMAND) -E cmake_symlink_library ../../../bin/libopenjp2.so.2.5.0 ../../../bin/libopenjp2.so.7 ../../../bin/libopenjp2.so//編譯依賴的Copenjp2_OBJECTS ="CMakeFiles/openjp2.dir/thread.c.o""CMakeFiles/openjp2.dir/bio.c.o""CMakeFiles/openjp2.dir/cio.c.o""CMakeFiles/openjp2.dir/dwt.c.o""CMakeFiles/openjp2.dir/event.c.o""CMakeFiles/openjp2.dir/ht_dec.c.o""CMakeFiles/openjp2.dir/image.c.o""CMakeFiles/openjp2.dir/invert.c.o""CMakeFiles/openjp2.dir/j2k.c.o""CMakeFiles/openjp2.dir/jp2.c.o""CMakeFiles/openjp2.dir/mct.c.o""CMakeFiles/openjp2.dir/mqc.c.o""CMakeFiles/openjp2.dir/openjpeg.c.o""CMakeFiles/openjp2.dir/opj_clock.c.o""CMakeFiles/openjp2.dir/pi.c.o""CMakeFiles/openjp2.dir/t1.c.o""CMakeFiles/openjp2.dir/t2.c.o""CMakeFiles/openjp2.dir/tcd.c.o""CMakeFiles/openjp2.dir/tgt.c.o""CMakeFiles/openjp2.dir/function_list.c.o""CMakeFiles/openjp2.dir/opj_malloc.c.o""CMakeFiles/openjp2.dir/sparse_array.c.o"
通過分析 build.make 文件發現需要依賴 depend.make、flags.make 和 link.txt,由以上內容可以分析出如下信息:

下面看下 flags.make 和 link.txt 文件的具體內容。
link.txt 的內容如下:
/usr/bin/cc-fPIC-O3-DNDEBUG-shared-Wl,-soname,libopenjp2.so.7-o../../../bin/libopenjp2.so.2.5.0CMakeFiles/openjp2.dir/thread.c.oCMakeFiles/openjp2.dir/bio.c.oCMakeFiles/openjp2.dir/cio.c.oCMakeFiles/openjp2.dir/dwt.c.oCMakeFiles/openjp2.dir/event.c.oCMakeFiles/openjp2.dir/ht_dec.c.oCMakeFiles/openjp2.dir/image.c.oCMakeFiles/openjp2.dir/invert.c.oCMakeFiles/openjp2.dir/j2k.c.oCMakeFiles/openjp2.dir/jp2.c.oCMakeFiles/openjp2.dir/mct.c.oCMakeFiles/openjp2.dir/mqc.c.oCMakeFiles/openjp2.dir/openjpeg.c.oCMakeFiles/openjp2.dir/opj_clock.c.oCMakeFiles/openjp2.dir/pi.c.oCMakeFiles/openjp2.dir/t1.c.oCMakeFiles/openjp2.dir/t2.c.oCMakeFiles/openjp2.dir/tcd.c.oCMakeFiles/openjp2.dir/tgt.c.oCMakeFiles/openjp2.dir/function_list.c.oCMakeFiles/openjp2.dir/opj_malloc.c.oCMakeFiles/openjp2.dir/sparse_array.c.o-lm-lpthread
從以上內容可以發現需要鏈接 -lm、-lpthread 這兩個庫。
flags.make 中的內容如下:
# CMAKE generated file: DO NOT EDIT!# Generated by "Unix Makefiles" Generator, CMake Version 3.16# compile C with /usr/bin/ccC_FLAGS = -fPIC -Wall -Wextra -Wconversion -Wunused-parameter -Wdeclaration-after-statement -Werror=declaration-after-statementC_DEFINES = -DMUTEX_pthread -Dopenjp2_EXPORTSC_INCLUDES=-I/home/water/openjpeg/openjpeg/build/src/lib/openjp2
從以上內容可以發現編譯需要的 C_FLAGS 信息。
3.提取有效信息
從上述分析可以提取以下信息:
需要包含的源文件:openjpeg/src/lib/openjp2/bio.copenjpeg/src/lib/openjp2/cio.copenjpeg/src/lib/openjp2/dwt.copenjpeg/src/lib/openjp2/event.copenjpeg/src/lib/openjp2/function_list.copenjpeg/src/lib/openjp2/ht_dec.copenjpeg/src/lib/openjp2/image.copenjpeg/src/lib/openjp2/invert.copenjpeg/src/lib/openjp2/j2k.copenjpeg/src/lib/openjp2/jp2.copenjpeg/src/lib/openjp2/mct.copenjpeg/src/lib/openjp2/mqc.copenjpeg/src/lib/openjp2/openjpeg.copenjpeg/src/lib/openjp2/opj_clock.copenjpeg/src/lib/openjp2/opj_malloc.copenjpeg/src/lib/openjp2/pi.copenjpeg/src/lib/openjp2/sparse_array.copenjpeg/src/lib/openjp2/t1.copenjpeg/src/lib/openjp2/t2.copenjpeg/src/lib/openjp2/tcd.copenjpeg/src/lib/openjp2/tgt.copenjpeg/src/lib/openjp2/thread.c需要包含的頭文件:src/lib/openjp2需要鏈接的庫:-lm -lpthread編譯器需要添加的C_FLAGS標記:C_FLAGS=-O3-DNDEBUG-fPIC-ffast-math-Wall-Wextra-Wconversion-Wunused-parameter-Wdeclaration-after-statement-Werror=declaration-after-statement
從上述內容中我們可以獲取到編譯 libopenjp2.so 所需的源文件、頭文件、鏈接庫、C_FLAGS 等信息。接下來就可以根據這些信息在 OpenHarmony 的三方庫文件夾下的 openjpeg 目錄下編寫 BUILD.gn 腳本,把 openjpeg 加入到 OpenHarmony 的編譯體系中。
五、將三方庫加入OpenHarmony的編譯體系
接下來演示一下如何把 OpenJPEG 開源庫通過 BUILD.gn 腳本添加到 OpenHarmony 工程中
表1:添加到工程后的目錄結構

1.OpenHarmony/build/subsystem_config.json 中添加 subsystem 節點。
"openjpeg":{"path":"third_party/openjpeg","name":"openjpeg"}
2.OpenHarmony/productdefine/common/products/rk3568.json 文件里面加入如下內容,添加板級相關的信息:
{"product_name": "rk3568","product_company": "hihope","product_device": "rk3568","version": "2.0","type": "standard","product_build_path": "device/hihope/build","parts":{"openjpeg:openjpeg_lib":{} #新增openjpeg_lib}}
3.third_partyopenjpeg ests 下添加 ohos.build 文件,以便系統可以編譯 tests 目錄下的測試文件:
third_partyopenjpeg ests下添加ohos.build文件:{"subsystem":"openjpeg","parts":{"openjpeg_lib":{"module_list":["http://third_party/openjpeg/tests:test_tile_decoder",#新增測試文件test_tile_decoder"http://third_party/openjpeg/tests:test_tile_encoder", #新增測試文件test_tile_encoder...........]}}}
4.OpenHarmony//third_party/openjpeg/ 目錄添加 BUILD.gn 文件,根據不同的系統生成靜態或者動態庫,如下:
if (defined(ohos_lite)) {import("http://build/lite/config/component/lite_component.gni")} else {import("http://build/ohos.gni")}#編譯CFLAG標記和需要鏈接的庫config("openjpeg_cflag_config") {cflags = ["-O3" ,"-DNDEBUG","-fPIC","-ffast-math","-Wall","-Wextra","-Wconversion","-Wunused-parameter","-Wdeclaration-after-statement","-Werror=declaration-after-statement",]ldflags = ["-lm","-lpthread",]}#需要包含的頭文件config("openjpeg_config") {include_dirs = ["http://third_party/openjpeg/src/lib/openjp2"]}#需要包含的源文件ohos_source_set("libopenjpeg_source") {sources = ["http://third_party/openjpeg/src/lib/openjp2/thread.c","http://third_party/openjpeg/src/lib/openjp2/bio.c","http://third_party/openjpeg/src/lib/openjp2/cio.c","http://third_party/openjpeg/src/lib/openjp2/dwt.c","http://third_party/openjpeg/src/lib/openjp2/event.c","http://third_party/openjpeg/src/lib/openjp2/ht_dec.c","http://third_party/openjpeg/src/lib/openjp2/image.c","http://third_party/openjpeg/src/lib/openjp2/invert.c","http://third_party/openjpeg/src/lib/openjp2/j2k.c","http://third_party/openjpeg/src/lib/openjp2/jp2.c","http://third_party/openjpeg/src/lib/openjp2/mct.c","http://third_party/openjpeg/src/lib/openjp2/mqc.c","http://third_party/openjpeg/src/lib/openjp2/openjpeg.c","http://third_party/openjpeg/src/lib/openjp2/opj_clock.c","http://third_party/openjpeg/src/lib/openjp2/pi.c","http://third_party/openjpeg/src/lib/openjp2/t1.c","http://third_party/openjpeg/src/lib/openjp2/t2.c","http://third_party/openjpeg/src/lib/openjp2/tcd.c","http://third_party/openjpeg/src/lib/openjp2/tgt.c","http://third_party/openjpeg/src/lib/openjp2/function_list.c","http://third_party/linu/src/lib/openjp2/opj_malloc.c","http://third_party/openjpeg/src/lib/openjp2/sparse_array.c",]}#根據不同系統編譯不同類型的庫lite類型的設備可以編程靜態庫,也可編成動態庫if (defined(ohos_lite)) {lite_library("libjpeg") {if (ohos_kernel_type == "liteos_m") {target_type = "static_library" #編譯成靜態庫libopenjpeg.a} else {target_type = "shared_library" #編成動態庫libopenjpeg.z.so}sources = libopenjpeg_source #依賴的源文件public_configs = [ ":openjpeg_config" ] #依賴的頭文件configs = [ ":openjpeg_cflag_config" ] #依賴的CFLAGS配置信息}} else {#標準系統編成動態庫,libopenjpeg.z.soohos_shared_library("openjpeg") {deps = [ ":libopenjpeg_source" ] #依賴的源文件public_configs = [ ":openjpeg_config" ] #依賴的頭文件配置信息configs = [ ":openjpeg_cflag_config" ] #依賴的CFLAGS配置信息part_name = "openjpeg_lib"}}
5.third_party/openjpeg/tests/ 目錄添加 BUILD.gn 文件,編譯測試文件,由于測試文件會依賴 OpenJPEG 庫,根據依賴關系(如下圖中的 deps)會鏈接到 thirdparty/openjpeg 下面的 BUILD.gn(即步驟 4 中的 BUILD.gn),最終此文件會編譯生成 libopenjpeg 庫。
third_party/openjpeg/tests/BUILD.gn 的內容如下:

以上幾個文件的具體調用關系如下圖所示:

通過 git status --ignored 命令可以查看我們修改什么內容,具體內如下:

通過以上操作以后,就可以在 OpenHarmony 編譯源碼了,編譯命令如下:
./build.sh--product-namerk3568--ccache
編譯完成以后可以在 /out/rk3568/packages/phone/system/lib 目錄下看到編譯生成的 libopenjpeg.z.so 文件。
water@ubuntu:~/OpenHarmony/out/rk3568/packages/phone/system/lib$ ls -l libopenjpeg.z.so-rwxr-xr-x1rootroot286148Mar2318:59libopenjpeg.z.so
同時,還可以在 out/rk3568/packages/phone/system/bin 目錄下看到我們編譯的測試文件 test_tile_encoder,如下所示:
water@ubuntu:~/openharmony/out/rk3568/packages/phone/system/bin$ ls -l test_test_decode_areatest_tile_decodertest_tile_encoder
把編譯完成的鏡像文件燒錄到 RK3568 開發板中,運行測試文件驗證整個庫的移植情況。
六、測試驗證
在開源庫的 tests 目錄下有很多測試用例,在 test 目錄下的 CMakeLists.txt 文件會生成一些測試文件來進行驗證,其中會給出一些測試方法,具體如下:


代碼工程編譯完成后,將鏡像文件燒錄到 RK3568 開發板中,在開發板 /system/bin 文件夾下可以發現,有編譯 tests 目錄后生成的測試文件,如下所示:
# ls -l test_*test_decode_areatest_open_jpeg.shtest_tile_decodertest_tile_encoder
在 data 目錄下創建 test 目錄:
pwd/datamkdirtest
把測試用例文件從 /bin 目錄下拷貝到 data/test 目錄下:
pwd/datacp/bin/test_*./
添加可執行權限:
chmod+xtest_tile_decoder
輸入如下命令:
./test_tile_encoder3200020001000100081tte1.j2k64644111256256
運行 test_tile_encoder,測試結果如下:

至此,整個 OpenJPEG 開源庫在 OpenHarmony 上的移植就完畢,感興趣的開發者可以動手移植自己的三方庫了。
附錄
開發過程中遇到的問題:
In file included from ../../third_party/openjpeg/src/lib/openjp2/thread.c:431:../../third_party/openjpeg/src/lib/openjp2/opj_includes.h:40:10: fatal error: 'opj_config_private.h' file not found#include"opj_config_private.h"
由于 opj_config_private.h 是由 cmake 生成的,因此需要在 Linux 下編譯整個 OpenJPEG 源碼,然后把生成的 opj_config_private.h 拷貝到相應的目錄下:cp ./build/src/lib/openjp2/opj_config_private.h /src/lib/./build/src/bin/common/opj_apps_config.h/cp ./build/src/lib/openjp2/opj_config.h /src/lib/openjp2/cp./build/src/bin/common/opj_apps_config.h./src/bin/common/
遇到重定義問題,在 third_party/openjpeg/tests/pdf2jp2.c 文件中把這行定義注釋掉:
../../third_party/openjpeg/tests/pdf2jp2.c:45:9: error: '_GNU_SOURCE' macro redefined [-Werror,-Wmacro-redefined]
RK3568 開發板相關的操作可以參考如下文檔:
RK3568 開發板標準設備上手-HelloWorld
https://gitee.com/openharmony-sig/knowledge_demo_temp/tree/master/docs/rk3568_helloworld
審核編輯 :李倩
-
Linux
+關注
關注
88文章
11758瀏覽量
219006 -
開源
+關注
關注
3文章
4203瀏覽量
46123 -
OpenHarmony
+關注
關注
33文章
3952瀏覽量
21095
原文標題:一文帶你讀懂如何移植三方庫到OpenHarmony
文章出處:【微信號:gh_e4f28cfa3159,微信公眾號:OpenAtom OpenHarmony】歡迎添加關注!文章轉載請注明出處。
發布評論請先 登錄
DEKRA德凱獲得沃爾沃汽車第三方實驗室認可資質
SEGGER Ozone調試器支持第三方調試工具
貨拉拉開源兩款三方庫,為鴻蒙應用高效開發貢獻力量
電子測試行業中的第三方檢測機構如何解決平臺靈活度低,維護困難等痛點問題?
飛書富文本組件庫RichTextVista開源
如何集成第三方支付API到電商網站
天合跟蹤獲得DNV第三方風洞測試審查報告
使用 Claroty SRA 優化第三方 OT 遠程訪問
小鵬汽車出席東盟-中國-海合會三方經濟論壇
貢獻 OpenHarmony 庫關鍵配置
基于RV1126開發板移植NCNN部署庫方法
總結移植三方庫到OpenHarmony的經驗
評論