SwiftyTesseract와 OpenCV를 넣으면 "duplicate symbol"버린 이야기
7016 단어 iOSSwiftOpenCVtesseract-ocrXcode
duplicate symbol
가 나와서 면을 먹었으므로 해결책을 비망록으로 남겨 둡니다.환경 정보
이름
버전
Xcode
12.3 (12C33)
Swift
5.3.2 (swiftlang-1200.0.45 clang-1200.0.32.28)
SwiftyTesseract
4.0.0
CMake
3.19.3
파이썬
2.7.16
xcode-select
2384
OpenCV
4.5.1
SwiftyTesseract와 OpenCV를 동일한 프로젝트에서 사용
두 프로젝트를 동일한 프로젝트에서 사용하는 절차를 보여줍니다.
SwiftyTesseract를 프로젝트에 추가
2021년 1월 19일 현재 SwiftyTesseract는 Swift Package Manager에서만 추가할 수 있습니다. 그래서 Swift Package Manager에서 추가합니다.
Xcode에서 File> Swift Packages> Add Package Dependency ...를 선택하고
입력란에 다음 GitHub URL을 입력합니다.
https://github.com/SwiftyTesseract/SwiftyTesseract
OpenCV를 프로젝트에 추가
iOS용 빌드
GitHub에서 OpenCV 받기 다음 platform/ios/
에 있는 다음 명령을 사용하여 iOS용 빌드합니다.
$ ./platform/ios/build_framework.py <output_dir>
빌드된 프레임워크 파일을 프로젝트에 추가
프로젝트 파일을 선택하고 왼쪽 창의 'TARGETS'에서 앱을 선택합니다.
그리고 "Build Phases > Link Binary With Libraries (n items)"를 선택하고 빌드로 출력된 "opencv2.framework"를 드래그 앤 드롭 등으로 추가합니다.
Other Linker Flags에 -all_load 추가
프로젝트 파일을 선택하고 왼쪽 창의 "PROJECT"에서 앱을 선택합니다.
Build Settings를 선택하여 Linking > Other Linker Flags에 -all_load
를 추가합니다.
libc++.tbd를 프로젝트에 추가
마찬가지로 프로젝트 파일의 "TARGETS"에서 앱을 선택합니다.
그런 다음 General > Frameworks, Libraries, and Embedded Content를 선택하고 왼쪽 하단의 + 버튼을 누릅니다.
검색창에 「libc++」라고 입력하면 「libc++.tbd」가 나온다고 생각하기 때문에 그것을 추가합니다.
시험에 빌드 해 보지만 ...
시도에 빌드해도이 시점에서는 작동하지 않습니다. 에러를 보면 「509 duplicate symbols for architecture x86_64(시뮬레이터라면×86_64, 실기라면 arm64)」라고 하는 대단한 수의 경합이 일어나고 있는 것을 알 수 있습니다.
해결책이지만 opencv2.framework에서 충돌이 발생한 파일을 삭제하여 해결할 수 있습니다.
충돌이 발생한 파일(.o 파일) 요약
오류에 따라 충돌이 발생하는 파일을 요약합니다. 저자의 환경에서는 다음 파일에서 충돌이 발생했습니다.
jutils.o pngrio.o pngwio.o jdcoefct.o jaricom.o jdmainct.o jdcolor.o pngerror.o jfdctint.o pngget.o pngrutil.o jmemmgr.o jccoefct.o jcmaster.o jidctflt.o pngpread.o jcprepct.o jerror.o pngset.o jctrans.o jcparam.o jdinput.o pngwtran.o jdarith.o jdsample.o jcomapi.o png.o pngrtran.o jchuff.o jddctmgr.o jidctfst.o jfdctfst.o pngwrite.o jfdctflt.o jdatasrc.o jdapistd.o pngmem.o jdapimin.o pngwutil.o jcdctmgr.o jdtrans.o jdhuff.o jdmaster.o jcapistd.o jdatadst.o jquant2.o jdmerge.o jmemnobs.o jccolor.o jdmarker.o jdpostct.o jcmarker.o jidctred.o jcarith.o jcmainct.o pngtrans.o jcinit.o jcsample.o jquant1.o pngread.o jidctint.o jcapimin.o
위의 목록은 나중에 명령에 인수로 먹일 때 사용할 수 있도록 텍스트 파일 등에 써 둡니다.
$ echo "jutils.o pngrio.o ..." > duplicate_lib_list
OpenCV를 아키텍처별로 분해
lipo 명령을 사용하여 프레임워크 폴더의 opencv2를 아키텍처별로 분해합니다.
먼저 무엇이 포함되어 있는지 아래 명령으로 확인하고,
$ cd opencv2.framework
$ lipo -info opencv2
Architectures in the fat file: opencv2 are: armv7 armv7s i386 x86_64 arm64
다음 명령으로 장미합니다.
$ lipo -thin armv7 opencv2 -output opencv2_armv7
$ lipo -thin armv7s opencv2 -output opencv2_armv7s
$ lipo -thin i386 opencv2 -output opencv2_i386
$ lipo -thin x86_64 opencv2 -output opencv2_x86_64
$ lipo -thin arm64 opencv2 -output opencv2_arm64
충돌이 발생한 파일 삭제
버려진 파일에 대해 다음 명령을 실행하여 충돌이 발생한 각 파일을 삭제합니다.
$ cat duplicate_lib_list | xargs ar -dv opencv2_armv7
$ cat duplicate_lib_list | xargs ar -dv opencv2_armv7s
$ cat duplicate_lib_list | xargs ar -dv opencv2_i386
$ cat duplicate_lib_list | xargs ar -dv opencv2_x86_64
$ cat duplicate_lib_list | xargs ar -dv opencv2_arm64
장미된 파일에서 재생성
다음 명령을 실행하여 opencv2를 재생성합시다.
$ lipo -create opencv2_arm64 opencv2_armv7 opencv2_armv7s opencv2_i386 opencv2_x86_64 -output opencv2
그리고는 중간에 만든 텍스트 파일 등의 불필요한 파일을 삭제하고 재빌드합시다.
경합이 해소되어 빌드할 수 있게 되어 있을 것입니다!
참고 기사
두 프로젝트를 동일한 프로젝트에서 사용하는 절차를 보여줍니다.
SwiftyTesseract를 프로젝트에 추가
2021년 1월 19일 현재 SwiftyTesseract는 Swift Package Manager에서만 추가할 수 있습니다. 그래서 Swift Package Manager에서 추가합니다.
Xcode에서 File> Swift Packages> Add Package Dependency ...를 선택하고
입력란에 다음 GitHub URL을 입력합니다.
https://github.com/SwiftyTesseract/SwiftyTesseract
OpenCV를 프로젝트에 추가
iOS용 빌드
GitHub에서 OpenCV 받기 다음
platform/ios/
에 있는 다음 명령을 사용하여 iOS용 빌드합니다.$ ./platform/ios/build_framework.py <output_dir>
빌드된 프레임워크 파일을 프로젝트에 추가
프로젝트 파일을 선택하고 왼쪽 창의 'TARGETS'에서 앱을 선택합니다.
그리고 "Build Phases > Link Binary With Libraries (n items)"를 선택하고 빌드로 출력된 "opencv2.framework"를 드래그 앤 드롭 등으로 추가합니다.
Other Linker Flags에 -all_load 추가
프로젝트 파일을 선택하고 왼쪽 창의 "PROJECT"에서 앱을 선택합니다.
Build Settings를 선택하여 Linking > Other Linker Flags에
-all_load
를 추가합니다.libc++.tbd를 프로젝트에 추가
마찬가지로 프로젝트 파일의 "TARGETS"에서 앱을 선택합니다.
그런 다음 General > Frameworks, Libraries, and Embedded Content를 선택하고 왼쪽 하단의 + 버튼을 누릅니다.
검색창에 「libc++」라고 입력하면 「libc++.tbd」가 나온다고 생각하기 때문에 그것을 추가합니다.
시험에 빌드 해 보지만 ...
시도에 빌드해도이 시점에서는 작동하지 않습니다. 에러를 보면 「509 duplicate symbols for architecture x86_64(시뮬레이터라면×86_64, 실기라면 arm64)」라고 하는 대단한 수의 경합이 일어나고 있는 것을 알 수 있습니다.
해결책이지만 opencv2.framework에서 충돌이 발생한 파일을 삭제하여 해결할 수 있습니다.
충돌이 발생한 파일(.o 파일) 요약
오류에 따라 충돌이 발생하는 파일을 요약합니다. 저자의 환경에서는 다음 파일에서 충돌이 발생했습니다.
jutils.o pngrio.o pngwio.o jdcoefct.o jaricom.o jdmainct.o jdcolor.o pngerror.o jfdctint.o pngget.o pngrutil.o jmemmgr.o jccoefct.o jcmaster.o jidctflt.o pngpread.o jcprepct.o jerror.o pngset.o jctrans.o jcparam.o jdinput.o pngwtran.o jdarith.o jdsample.o jcomapi.o png.o pngrtran.o jchuff.o jddctmgr.o jidctfst.o jfdctfst.o pngwrite.o jfdctflt.o jdatasrc.o jdapistd.o pngmem.o jdapimin.o pngwutil.o jcdctmgr.o jdtrans.o jdhuff.o jdmaster.o jcapistd.o jdatadst.o jquant2.o jdmerge.o jmemnobs.o jccolor.o jdmarker.o jdpostct.o jcmarker.o jidctred.o jcarith.o jcmainct.o pngtrans.o jcinit.o jcsample.o jquant1.o pngread.o jidctint.o jcapimin.o
위의 목록은 나중에 명령에 인수로 먹일 때 사용할 수 있도록 텍스트 파일 등에 써 둡니다.
$ echo "jutils.o pngrio.o ..." > duplicate_lib_list
OpenCV를 아키텍처별로 분해
lipo 명령을 사용하여 프레임워크 폴더의 opencv2를 아키텍처별로 분해합니다.
먼저 무엇이 포함되어 있는지 아래 명령으로 확인하고,
$ cd opencv2.framework
$ lipo -info opencv2
Architectures in the fat file: opencv2 are: armv7 armv7s i386 x86_64 arm64
다음 명령으로 장미합니다.
$ lipo -thin armv7 opencv2 -output opencv2_armv7
$ lipo -thin armv7s opencv2 -output opencv2_armv7s
$ lipo -thin i386 opencv2 -output opencv2_i386
$ lipo -thin x86_64 opencv2 -output opencv2_x86_64
$ lipo -thin arm64 opencv2 -output opencv2_arm64
충돌이 발생한 파일 삭제
버려진 파일에 대해 다음 명령을 실행하여 충돌이 발생한 각 파일을 삭제합니다.
$ cat duplicate_lib_list | xargs ar -dv opencv2_armv7
$ cat duplicate_lib_list | xargs ar -dv opencv2_armv7s
$ cat duplicate_lib_list | xargs ar -dv opencv2_i386
$ cat duplicate_lib_list | xargs ar -dv opencv2_x86_64
$ cat duplicate_lib_list | xargs ar -dv opencv2_arm64
장미된 파일에서 재생성
다음 명령을 실행하여 opencv2를 재생성합시다.
$ lipo -create opencv2_arm64 opencv2_armv7 opencv2_armv7s opencv2_i386 opencv2_x86_64 -output opencv2
그리고는 중간에 만든 텍스트 파일 등의 불필요한 파일을 삭제하고 재빌드합시다.
경합이 해소되어 빌드할 수 있게 되어 있을 것입니다!
참고 기사
Reference
이 문제에 관하여(SwiftyTesseract와 OpenCV를 넣으면 "duplicate symbol"버린 이야기), 우리는 이곳에서 더 많은 자료를 발견하고 링크를 클릭하여 보았다 https://qiita.com/ryo_qiita/items/494f6c4faf1f329f7004텍스트를 자유롭게 공유하거나 복사할 수 있습니다.하지만 이 문서의 URL은 참조 URL로 남겨 두십시오.
우수한 개발자 콘텐츠 발견에 전념 (Collection and Share based on the CC Protocol.)