GCC 설치 (`macOS`, `Windows`)

macOS 및 Windows 에 GCC 설치하기 MAC OS brew : macOS 용 패키지 관리자 https://brew.sh/index_ko{:target="_blank"} brew 사용 gcc 설치 Command line tools 설치 xcode 없이 개발툴 설치 $ xcode-select --install clang 이 설치되고 gcc로 심볼링 링크 걸려 있음 $ gcc -v Configured with: --prefix=/Library/Developer/CommandLineTools/usr --with-gxx-include-dir=/Library/Developer/CommandLineTools/SDKs/MacOSX.sdk/usr/include/c++/4.2.1 Apple clang version 12.0.5 (clang-1205.0.22.11) Target: arm64-apple-darwin20.6.0 Thread model: posix InstalledDir: /Library/Developer/CommandLineTools/usr/bin GCC (G++) 설치 # 특정 버전으로 설치 가능 $ brew search gcc ==> Formulae gcc gcc@5 gcc@8 libgccjit ghc ncc gcc@10 gcc@6 gcc@9 x86_64-elf-gcc scc gcc@4.9 gcc@7 i686-elf-gcc grc tcc ==> Casks gcc-arm-embedded # 기본(최신) 버전 설치 $ brew install gcc ==> Auto-updated Homebrew! Updated 1 tap (homebrew/core). ==> Updated Formulae Updated 1 formula. ==> Downloading https://ghcr.io/v2/homebrew/core/gcc/manifests/11.2.0 Already downloaded: /Users/cdecl/Library/Caches/Homebrew/downloads/210783e77b227b8210d559abfe3514cdb95c915619fa3f785ad212120d6a36f9--gcc-11.2.0.bottle_manifest.json ==> Downloading https://ghcr.io/v2/homebrew/core/gcc/blobs/sha256:23ec727fa684a9f65cf9f55d61d208486d5202fb6112585a01426a Already downloaded: /Users/cdecl/Library/Caches/Homebrew/downloads/8d1fae8a356d50aa911004b768eff64c241e170ce9be66e684b819fc4f67fc7c--gcc--11.2.0.arm64_big_sur.bottle.tar.gz ==> Pouring gcc--11.2.0.arm64_big_sur.bottle.tar.gz 🍺 /opt/homebrew/Cellar/gcc/11.2.0: 1,412 files, 339.5MB 심볼릭링크 설정 및 PATH 설정 $ cd /opt/homebrew/Cellar/gcc/11.2.0 $ ls -l ... -rwxr-xr-x 1 cdecl admin 1.7M 8 28 13:41 g++-11 -rwxr-xr-x 1 cdecl admin 1.7M 8 28 13:41 gcc-11 ... $ ln -s g++-11 g++ $ ln -s gcc-11 gcc .zshrc or .bashrc export PATH=/opt/homebrew/Cellar/gcc/11.2.0/bin:$PATH $ g++ -v Using built-in specs. COLLECT_GCC=g++ COLLECT_LTO_WRAPPER=/opt/homebrew/Cellar/gcc/11.2.0/libexec/gcc/aarch64-apple-darwin20/11.1.0/lto-wrapper Target: aarch64-apple-darwin20 Configured with: ../configure --prefix=/opt/homebrew/Cellar/gcc/11.2.0 --libdir=/opt/homebrew/Cellar/gcc/11.2.0/lib/gcc/11 --disable-nls --enable-checking=release --enable-languages=c,c++,objc,obj-c++,fortran --program-suffix=-11 --with-gmp=/opt/homebrew/opt/gmp --with-mpfr=/opt/homebrew/opt/mpfr --with-mpc=/opt/homebrew/opt/libmpc --with-isl=/opt/homebrew/opt/isl --with-zstd=/opt/homebrew/opt/zstd --with-pkgversion='Homebrew GCC 11.2.0' --with-bugurl=https://github.com/Homebrew/homebrew-core/issues --build=aarch64-apple-darwin20 --with-system-zlib --disable-multilib --with-native-system-header-dir=/usr/include --with-sysroot=/Library/Developer/CommandLineTools/SDKs/MacOSX.sdk Thread model: posix Supported LTO compression algorithms: zlib zstd gcc version 11.1.0 (Homebrew GCC 11.2.0) Windows chocolatey chocolatey : Windows 용 패키지 관리자 https://chocolatey.org/{:target="_blank"} choco 사용 gcc 설치 GCC (G++) 설치 패키지가 2개중에 하나 선택 mingw : https://community.chocolatey.org/packages/mingw{:target="_blank"} winlibs : https://community.chocolatey.org/packages/winlibs{:target="_blank"} winlibs가 버전이 높고 mingw는 버전인 올라가면서 posix thread가 문제가 있음 ...

August 27, 2021 · Byung Kyu KIM

Docker 내부 네트워크 상태 확인

netstat Host 머신에서 netstat 명령으로 docker container의 네트워크 상태가 확인 안됨 물론 container 내부에서 실행하면 되지만… docker container는 bridge 네트워크 기반으로 운영이 되므로 Host Network 에서는 노출이 안됨 # docker 실행 $ docker run -d -p 8081:80 --name=mvcapp cdecl/mvcapp 4fafaf418f84bf6541a1301b4422f825c58fa20b11d1190e87a3e23eea7a6825 # Host 에서는 publsh port (listen) 정보만 노출 $ netstat -ntl | grep 8081 tcp6 0 0 :::8081 :::* LISTEN # ip 현황 $ ip a ... 2: eth0: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc mq state UP group default qlen 1000 link/ether 00:15:5d:3a:4a:00 brd ff:ff:ff:ff:ff:ff inet 192.168.137.100/24 brd 192.168.137.255 scope global noprefixroute eth0 valid_lft forever preferred_lft forever 4: docker0: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc noqueue state UP group default <-- docker bridge link/ether 02:42:58:c6:1b:23 brd ff:ff:ff:ff:ff:ff inet 10.1.0.1/24 brd 10.1.0.255 scope global docker0 valid_lft forever preferred_lft forever ... # bridge network $ docker inspect -f '{{.NetworkSettings.Gateway}}' mvcapp 10.1.0.1 # 라우팅 정보 $ netstat -r Kernel IP routing table Destination Gateway Genmask Flags MSS Window irtt Iface default gateway 0.0.0.0 UG 0 0 0 eth0 10.1.0.0 0.0.0.0 255.255.255.0 U 0 0 0 docker0 <-- docker bridge 10.42.0.0 0.0.0.0 255.255.255.0 U 0 0 0 cni0 192.168.137.0 0.0.0.0 255.255.255.0 U 0 0 0 eth0 nsenter https://github.com/jpetazzo/nsenter{:target="_blank"} 격리되어 있는 namespace enter 진입하는 명령 It is a small tool allowing to enter into namespaces. Technically, it can enter existing namespaces, or spawn a process into a new set of namespaces. ...

August 26, 2021 · Byung Kyu KIM

Golang, Cgo

Cgo enables the creation of Go packages that call C code. Cgo https://pkg.go.dev/cmd/cgo{:target="_blank"} Golang에서 C 코드를 통합 할 수 있도록 만든 의사 패키지 C코드 - Go 파일 통합 예제 import "C" 바로 윗 부분의 주석 /* */ or // 으로 C코드 작성 C 함수, 변수 영역 접근시, C 의 패키지 명으로 접근 함수, 변수선언, #include 선행처리지시자 등 일반적인 C 코드 cgo Cheat Sheet : https://gist.github.com/zchee/b9c99695463d8902cd33{:target="_blank"} package main /* #include <stdio.h> // printf #include <stdlib.h> // free (C.free) void println(const char *s) { printf("%s\n", s); } */ import "C" import ( "fmt" "unsafe" ) func main() { s := C.CString("c lang println") C.free(unsafe.Pointer(s)) C.println(s) fmt.Println("golang println") } $ go mod init main $ go build $ ./main c lang println golang println C코드 통합 - 별도 파일(C/C++)로 구성 같은 디렉토리의 C/C++ file extention 의 경우 기본 gcc(g++)로 빌드 및 링크 별도 파일의 경우 C++ 코드도 작성이 가능하나, golang 에서는 C언어 (Name mangling) 방식만 지원 Name mangling: 컴파일러가 함수명이나 변수이름을 특정한 규칙으로 변경 C++의 경우는 함수 Overloading으로 인해 C언어와 규칙이 다름 extern "C": C언어 방식의 Name mangling으로 처리 $ tree ├── go.mod ├── main.go └── print.cpp package main // #include <stdlib.h> // free // void println(char *s); import "C" import ( "fmt" "unsafe" ) func main() { s := C.CString("cpp println") C.free(unsafe.Pointer(s)) C.println(s) fmt.Println("golang println") } #include <iostream> using namespace std; extern "C" void println(const char *s); void println(const char *s) { cout << s << endl; } $ go build $ ./main cpp println Static, Dynamic library link $ tree ├── go.mod ├── main.go └── native ├── print.cpp └── print.h // print.h #pragma once #ifdef __cplusplus extern "C" { #endif void println(const char *s); #ifdef __cplusplus } #endif // print.cpp #include <iostream> #include "print.h" void println(const char *s) { std::cout << s << std::endl; } #cgo LDFLAG: 컴파일러 라이브러리 링크 옵션 지정 #cgo CFLAGS: 컴파일러 컴파일 옵션 package main // #cgo LDFLAGS: -Lnative -lprint -lstdc++ // #include <stdlib.h> // #include "native/print.h" import "C" import ( "fmt" "unsafe" ) func main() { s := C.CString("cpp println") C.free(unsafe.Pointer(s)) C.println(s) fmt.Println("golang println") } Static link $ cd native $ g++ -c print.cpp $ ar -cr libprint.a print.o $ cd .. $ go build $ ./main cpp println golang println Dynamic Link $ cd native $ g++ -dynamic -fPIC -o libprint.so -c libprint.cpp $ cd .. $ go build # Mac : export DYLD_LIBRARY_PATH=$(pwd)/native $ export LD_LIBRARY_PATH=/root/cgo/native $ ./main cpp println golang println 의존성 확인 Linux $ ldd ./main linux-vdso.so.1 (0x0000ffff9446a000) libprint.so => /root/cgo/native/libprint.so (0x0000ffff94428000) libpthread.so.0 => /lib/aarch64-linux-gnu/libpthread.so.0 (0x0000ffff943f7000) libc.so.6 => /lib/aarch64-linux-gnu/libc.so.6 (0x0000ffff94281000) libstdc++.so.6 => /usr/lib/aarch64-linux-gnu/libstdc++.so.6 (0x0000ffff940a9000) /lib/ld-linux-aarch64.so.1 (0x0000ffff9443a000) libm.so.6 => /lib/aarch64-linux-gnu/libm.so.6 (0x0000ffff93ffe000) libgcc_s.so.1 => /lib/aarch64-linux-gnu/libgcc_s.so.1 (0x0000ffff93fda000) Mac $ otool -L ./main ./main: libprint.so (compatibility version 0.0.0, current version 0.0.0) /usr/lib/libc++.1.dylib (compatibility version 1.0.0, current version 905.6.0) /System/Library/Frameworks/CoreFoundation.framework/Versions/A/CoreFoundation (compatibility version 150.0.0, current version 1775.118.101) /usr/lib/libSystem.B.dylib (compatibility version 1.0.0, current version 1292.100.5) 예제 : char * 다루기 - string → *C.char : C.CString(string) // C.free(unsafe.Pointer(*C.char)) 메모리 해제 필수 - *C.char → string : C.GoString(*C.char) - []C.char' : byte slice → *C.char // buff := make([]byte, 128), (*C.char)(unsafe.Pointer(&buff[0])) - *C.char, C.int → string : C.GoStringN(*C.char, C.int) package main /* #include <stdlib.h> #include <string.h> */ import "C" import ( "fmt" "unsafe" ) func getptr(buff []byte) *C.char { return (*C.char)(unsafe.Pointer(&buff[0])) } func main() { buff := make([]byte, 128) s := C.CString("Hello") defer C.free(unsafe.Pointer(s)) C.strcpy(getptr(buff), s) fmt.Println(string(buff)) }

August 23, 2021 · Byung Kyu KIM

Docker Private Registry

Docker Private Registry 구성 Registry 실행 docker-compose.yml version: '3' services: registry: image: registry container_name: registry restart: always ports: - 5000:5000 environment: REGISTRY_HTTP_ADDR: 0.0.0.0:5000 volumes: - registry:/var/lib/registry - ./config.yml:/etc/docker/registry/config.yml volumes: registry: # 실행 $ docker-compose up -d $ curl -s http://localhost:5000/v2/_catalog {"repositories":[]} SSL 적용 version: '3' services: registry: image: registry container_name: private_registry restart: always ports: - 5000:5000 environment: REGISTRY_HTTP_ADDR: 0.0.0.0:5000 REGISTRY_HTTP_TLS_CERTIFICATE: /certs/domain-pem.pem REGISTRY_HTTP_TLS_KEY: /certs/domain-pem.key volumes: - registry:/var/lib/registry - ./config.yml:/etc/docker/registry/config.yml - ./certs:/certs volumes: registry: Image Push 테스트용 이미지 태깅 # get alpine images $ docker pull alpine $ docker pull alpine:3.13 # tagging $ docker tag alpine localhost:5000/cdecl/alpine:latest $ docker tag alpine:3.13 localhost:5000/cdecl/alpine:3.13 $ docker images REPOSITORY TAG IMAGE ID CREATED SIZE alpine latest ae607a46d002 2 weeks ago 5.33MB localhost:5000/cdecl/alpine latest ae607a46d002 2 weeks ago 5.33MB alpine 3.13 81efc9693413 2 months ago 5.35MB localhost:5000/cdecl/alpine 3.13 81efc9693413 2 months ago 5.35MB Image Push # image push $ docker push localhost:5000/cdecl/alpine:3.13 The push refers to repository [localhost:5000/cdecl/alpine] c55d5dbdab40: Layer already exists 3.13: digest: sha256:55fc95a51d97f7b76b124f3b581a58ebf5555d12574f16087de3971a12724dd4 size: 528 $ docker push localhost:5000/cdecl/alpine:latest The push refers to repository [localhost:5000/cdecl/alpine] 5bfa694cc00a: Layer already exists latest: digest: sha256:bd9137c3bb45dbc40cde0f0e19a8b9064c2bc485466221f5e95eb72b0d0cf82e size: 528 # Catalog list $ curl -s http://localhost:5000/v2/_catalog {"repositories":["cdecl/alpine"]} # Tag 정보 $ curl -s http://localhost:5000/v2/cdecl/alpine/tags/list {"name":"cdecl/alpine","tags":["latest","3.13"]} Image Pull $ docker pull localhost:5000/cdecl/alpine Using default tag: latest latest: Pulling from cdecl/alpine Digest: sha256:bd9137c3bb45dbc40cde0f0e19a8b9064c2bc485466221f5e95eb72b0d0cf82e Status: Downloaded newer image for localhost:5000/cdecl/alpine:latest localhost:5000/cdecl/alpine:latest Image Delete Tag 확인 -> Manifests 확인 -> Manifests 이미지 삭제 # Tag 정보 확인 $ curl -s http://localhost:5000/v2/cdecl/alpine/tags/list {"name":"cdecl/alpine","tags":["latest","3.13"]} # Tag의 Manifest 정보확인 - headers 확인 # <registry-url>/v2/<image-path-name>/manifests/<tag> $ curl -s -I -H "Accept: application/vnd.docker.distribution.manifest.v2+json" \ http://localhost:5000/v2/cdecl/alpine/manifests/latest HTTP/1.1 200 OK Content-Length: 528 Content-Type: application/vnd.docker.distribution.manifest.v2+json Docker-Content-Digest: sha256:bd9137c3bb45dbc40cde0f0e19a8b9064c2bc485466221f5e95eb72b0d0cf82e Docker-Distribution-Api-Version: registry/2.0 Etag: "sha256:bd9137c3bb45dbc40cde0f0e19a8b9064c2bc485466221f5e95eb72b0d0cf82e" # Manifest 정보로 이미지 삭제 # Docker-Content-Digest: <sha256:로 시작하는 해쉬 문자열> $ curl -s -XDELETE http://localhost:5000/v2/cdecl/alpine/manifests/sha256:bd9137c3bb45dbc40cde0f0e19a8b9064c2bc485466221f5e95eb72b0d0cf82e # 확인 $ curl -s http://localhost:5000/v2/cdecl/alpine/tags/list {"name":"cdecl/alpine","tags":["3.13"]} Delete marked manifests $ curl -sS http://localhost:5000/v2/cdecl/alpine/tags/list {"name":"cdecl/alpine","tags":null} $ docker exec -it registry bin/registry garbage-collect /etc/docker/registry/config.yml cdecl/alpine 0 blobs marked, 3 blobs and 0 manifests eligible for deletion blob eligible for deletion: sha256:81efc9693413c6292235ea2c29ea07c149701140b98df6c1998bb91d41acf802 INFO[0000] Deleting blob: /docker/registry/v2/blobs/sha256/81/81efc9693413c6292235ea2c29ea07c149701140b98df6c1998bb91d41acf802 go.version=go1.11.2 instance.id=d8bbbd10-232a-457a-9ceb-312b7317da5f service=registry blob eligible for deletion: sha256:55fc95a51d97f7b76b124f3b581a58ebf5555d12574f16087de3971a12724dd4 INFO[0000] Deleting blob: /docker/registry/v2/blobs/sha256/55/55fc95a51d97f7b76b124f3b581a58ebf5555d12574f16087de3971a12724dd4 go.version=go1.11.2 instance.id=d8bbbd10-232a-457a-9ceb-312b7317da5f service=registry blob eligible for deletion: sha256:595b0fe564bb9444ebfe78288079a01ee6d7f666544028d5e96ba610f909ee43 INFO[0000] Deleting blob: /docker/registry/v2/blobs/sha256/59/595b0fe564bb9444ebfe78288079a01ee6d7f666544028d5e96ba610f909ee43 go.version=go1.11.2 instance.id=d8bbbd10-232a-457a-9ceb-312b7317da5f service=registry 위 작업으로는 물리적인 데이터가 삭제 안됨 # 물리적인 파일 삭제 $ docker exec -it registry rm -rf /var/lib/registry/docker/registry/v2/repositories/cdecl Script registry-image-delete.sh #!/bin/bash URI="$1" NAME="$2" TAG="$3" if [[ -z "$URI" ]]; then echo "Usage: $0 <URI> <NAME> [<TAG>]" exit -1 fi if [[ -z "$NAME" ]]; then echo "Usage: $0 $URI <NAME> [<TAG>]" echo curl -sS $URI/v2/_catalog | jq -r '.repositories[]' echo exit -1 fi if [[ -z "$TAG" ]]; then echo "Usage: $0 $URI $NAME [<TAG>]" echo curl -sS $URI/v2/$NAME/tags/list | jq -r '.tags[]' echo exit -1 fi MANIFESTS=$(curl -sS -I -H "Accept: application/vnd.docker.distribution.manifest.v2+json" \ $URI/v2/$NAME/manifests/$TAG | grep -i Docker-Content-Digest | awk '{print $2}') if [[ -z "$MANIFESTS" ]]; then echo "No manifest found for $NAME:$TAG" exit -1 fi echo $MANIFESTS echo echo curl -sS -XDELETE $URI/v2/$NAME/manifests/$MANIFESTS echo

August 22, 2021 · Byung Kyu KIM

oh-my-zsh so slow (WSL)

oh-my-zsh 이 느린 경우 해결 방법 (특히 WSL) oh-my-zsh so slow Theme 가 느린 경우는 Pass git 관리 디렉토리 진입시 현저히 느려지는 경우 $ git config --global oh-my-zsh.hide-status 1 $ git config --global oh-my-zsh.hide-dirty 1 $ git config --global -l oh-my-zsh.hide-status=1 oh-my-zsh.hide-dirty=1

August 22, 2021 · Byung Kyu KIM

Mac Application

Mac 설치 어플리케이션 brew 패키지 관리자 https://brew.sh/index_ko{:target="_blank"} # 설치 $ brew search iterm2 $ brew install iterm2 karabiner-elements brew install brew search karabiner https://karabiner-elements.pqrs.org/{:target="_blank"} 오른쪽 command 버튼 한영키로 매핑 iTerm2 터미널 brew install iterm2 Zsh, Oh My Zsh https://github.com/ohmyzsh/ohmyzsh{:target="_blank"} # zsh install $ brew install zsh # oh my zsh VSCode https://code.visualstudio.com/{:target="_blank"} Docker https://www.docker.com/get-started{:target="_blank"} Dbeaver DB Tool brew install dbeaver-community IINA 동영상 플레이어 brew install iina https://iina.io/{:target="_blank"} Mounty NTFS Mount brew search mounty https://mounty.app/{:target="_blank"} Keka 압축프로그램 brew install keka https://www.keka.io/ko/{:target="_blank"}

August 19, 2021 · Byung Kyu KIM

Vim 최소 설정

vim 최소 설정 .vimrc set ts=4 set autoindent set cindent set hlsearch set showmatch if has("syntax") syntax on endif

August 19, 2021 · Byung Kyu KIM

Httplib (cpp-httplib) Sample

Introduction https://github.com/yhirose/cpp-httplib{:target="_blank"} A C++11 single-file header-only cross platform HTTP/HTTPS library. This is a multi-threaded ‘blocking’ HTTP library header-only 라이브러리로 Server와 Client Http 지원 SSL을 위한 OpenSSL 필요 cpprestsdk비해 가볍고, 쉽게 사용 가능 Httplib package install (w/ vcpkg) https://github.com/microsoft/vcpkg{:target="_blank"} vcpkg 통해서 패키지 설치 header-only로 바로 사용가능하나 OpenSSL 필요시 패키지 설치가 용이 # --triplet=x64-windows-static $ vcpkg.exe install cpp-httplib openssl --triplet=x64-windows-static ... The package cpp-httplib:x64-windows-static is header only and can be used from CMake via: find_path(CPP_HTTPLIB_INCLUDE_DIRS "httplib.h") target_include_directories(main PRIVATE ${CPP_HTTPLIB_INCLUDE_DIRS}) The package openssl is compatible with built-in CMake targets: find_package(OpenSSL REQUIRED) target_link_libraries(main PRIVATE OpenSSL::SSL OpenSSL::Crypto) Json test https://github.com/nlohmann/json{:target="_blank"} $ vcpkg.exe install nlohmann-json --triplet=x64-windows-static The package nlohmann-json:x64-windows-static provides CMake targets: find_package(nlohmann_json CONFIG REQUIRED) target_link_libraries(main PRIVATE nlohmann_json nlohmann_json::nlohmann_json) Sample code HTTPS 호출을 위해 CPPHTTPLIB_OPENSSL_SUPPORT 매크로가 정의 되어 있어야 함 정의하지 않고 HTTPS 호출시 : 'https' scheme is not supported. using namespace std; std namespace 노출시 byte 타입 정의 모호함으로 인한 에러 발생 표준 라이브러리 보다 먼저 선언되던가 using namespace std;를 피해야 함 ‘byte’: 모호한 기호입니다. #define CPPHTTPLIB_OPENSSL_SUPPORT #include <httplib.h> #include <iostream> using namespace std; #include <nlohmann/json.hpp> using json = nlohmann::json; void HttpRequest() { httplib::Client cli("https://httpbin.org"); { auto resp = cli.Get("/get"); cout << "status: " << resp->status << endl; cout << resp->body << endl; } { auto resp = cli.Post("/post"); cout << "status: " << resp->status << endl; cout << resp->body << endl; auto js = json::parse(resp->body); cout << "User-Agent: " << js["headers"]["User-Agent"] << endl; } } int main() { try { HttpRequest(); } catch (exception &e) { cerr << e.what() << endl; } catch (...) { cerr << "catch ..." << endl; } return 0; } CMakeLists.txt cmake_minimum_required(VERSION 3.11) project(main) set(CMAKE_CXX_STANDARD 17) add_executable(main main.cpp) target_compile_options(main PRIVATE /MT) find_package(OpenSSL REQUIRED) target_link_libraries(main PRIVATE OpenSSL::SSL OpenSSL::Crypto) find_path(CPP_HTTPLIB_INCLUDE_DIRS "httplib.h") target_include_directories(main PRIVATE ${CPP_HTTPLIB_INCLUDE_DIRS}) find_package(nlohmann_json CONFIG REQUIRED) target_link_libraries(main PRIVATE nlohmann_json nlohmann_json::nlohmann_json) $ mkdir build && cd build # x64-windows-static $ cmake -G "Visual Studio 16 2019" -A x64 .. -DCMAKE_TOOLCHAIN_FILE=D:/Lib/vcpkg/scripts/buildsystems/vcpkg.cmake -DVCPKG_TARGET_TRIPLET=x64-windows-static Build & Run # build $ echo cmake --build . --config Release > make.bat $ make.bat # run $ Release\main.exe status: 200 { "args": {}, "headers": { "Accept": "*/*", "Cache-Control": "max-stale=0", "Host": "httpbin.org", "User-Agent": "cpp-httplib/0.9", "X-Amzn-Trace-Id": "Root=1-611dba9f-0bdb46bb04c05b410da75cf4", "X-Bluecoat-Via": "ce2cfae06b3f12b4" }, "origin": "xx.xx.xx.xx", "url": "https://httpbin.org/get" } status: 200 { "args": {}, "data": "", "files": {}, "form": {}, "headers": { "Accept": "*/*", "Content-Length": "0", "Host": "httpbin.org", "User-Agent": "cpp-httplib/0.9", "X-Amzn-Trace-Id": "Root=1-611dba9f-091d99a41e5b3c023550162f", "X-Bluecoat-Via": "ce2cfae06b3f12b4" }, "json": null, "origin": "xx.xx.xx.xx", "url": "https://httpbin.org/post" } User-Agent: "cpp-httplib/0.9"

August 18, 2021 · Byung Kyu KIM

Vcpkg Basic

https://vcpkg.io/{:target="_blank"} Vcpkg helps you manage C and C++ libraries on Windows, Linux and MacOS. This tool and ecosystem are constantly evolving, and we always appreciate contributions! Introduction https://github.com/microsoft/vcpkg{:target="_blank"} MS에서 만든 C++ Library Package 관리 (Cross Platform) Vcpkg install Git 이 필요하고, bootstrap-vcpkg 실행으로 필요한 툴을 다운로드(빌드)하는 작업을 수행 vcpkg.exe 생성 $ git clone https://github.com/microsoft/vcpkg $ cd vcpkg # windows $ bootstrap-vcpkg.bat # linux $ ./bootstrap-vcpkg.sh Package search & install triplet : Target configuration set 설치시 triplet 을 지정하지 않으면 설치되어 있는 기본 C++ Toolset 으로 지정 Windows의 경우 x86-windows default 주요 Triplet list vcpkg help triplet $ vcpkg help triplet Available architecture triplets VCPKG built-in triplets: ... x64-windows-static x64-windows x86-windows ... VCPKG community triplets: ... x64-windows-static-md x86-windows-static-md x86-windows-static x64-mingw-dynamic x64-mingw-static x86-mingw-dynamic x86-mingw-static x64-linux ... Search vcpkg search # Package search $ vcpkg search fmt fmt 7.1.3#5 Formatting library for C++. ... The search result may be outdated. Run `git pull` to get the latest results. Install vcpkg install vcpkg search 에서 찾은 패키지를 triplet 을 지정하여 설치 설치가 완료되면 프로젝트 CMakeLists.txt 넣을 find_package 문 표시 # Package 별로 triplet 지정 $ vcpkg.exe install fmt:x64-windows-static nlohmann-json:x64-windows-static # triplet 공통 지정 $ vcpkg.exe install fmt nlohmann-json --triplet=x64-windows-static ... The package fmt provides CMake targets: find_package(fmt CONFIG REQUIRED) target_link_libraries(main PRIVATE fmt::fmt) # Or use the header-only version find_package(fmt CONFIG REQUIRED) target_link_libraries(main PRIVATE fmt::fmt-header-only) The package nlohmann-json:x64-windows-static provides CMake targets: find_package(nlohmann_json CONFIG REQUIRED) target_link_libraries(main PRIVATE nlohmann_json nlohmann_json::nlohmann_json) 설치된 리스트 vcpkg list # Package installed list $ vcpkg list benchmark:x64-mingw-static 1.5.5 A library to support the benchmarking of functio... benchmark:x64-windows-static 1.5.5 A library to support the benchmarking of functio... cpp-httplib:x64-mingw-static 0.9.1 A single file C++11 header-only HTTP/HTTPS serve... cpp-httplib:x64-windows-static 0.9.1 A single file C++11 header-only HTTP/HTTPS serve... fmt:x64-windows 7.1.3#5 Formatting library for C++. It can be used as a ... fmt:x64-windows-static 7.1.3#5 Formatting library for C++. It can be used as a ... nlohmann-json:x64-mingw-static 3.9.1 JSON for Modern C++ nlohmann-json:x64-windows-static 3.9.1 JSON for Modern C++ openssl:x64-mingw-static 1.1.1k#8 OpenSSL is an open source project that provides ... openssl:x64-windows-static 1.1.1k#8 OpenSSL is an open source project that provides ... vcpkg-cmake-config:x64-windows 2021-05-22#1 vcpkg-cmake:x64-windows 2021-07-30 zlib:x64-mingw-static 1.2.11#11 A compression library zlib:x64-windows-static 1.2.11#11 A compression library Integrate install vcpkg integrate install Windows Visual Studio에서 vcpkg 라이브러리를 별도 설정 없이 바로 사용 $ vcpkg integrate install Applied user-wide integration for this vcpkg root. All MSBuild C++ projects can now #include any installed libraries. Linking will be handled automatically. Installing new libraries will make them instantly available. CMake projects should use: "-DCMAKE_TOOLCHAIN_FILE=D:/Lib/vcpkg/scripts/buildsystems/vcpkg.cmake" vcpkg 명령어 # Vcpkg package management program version 2021-08-12-85ab112d5ee102bc6eac8cdbbfdd173a71374e04 $ vcpkg help Commands: vcpkg search [pat] Search for packages available to be built vcpkg install <pkg>... Install a package vcpkg remove <pkg>... Uninstall a package vcpkg remove --outdated Uninstall all out-of-date packages vcpkg list List installed packages vcpkg update Display list of packages for updating vcpkg upgrade Rebuild all outdated packages vcpkg x-history <pkg> (Experimental) Shows the history of CONTROL versions of a package vcpkg hash <file> [alg] Hash a file by specific algorithm, default SHA512 vcpkg help topics Display the list of help topics vcpkg help <topic> Display help for a specific topic vcpkg integrate install Make installed packages available user-wide. Requires admin privileges on first use vcpkg integrate remove Remove user-wide integration vcpkg integrate project Generate a referencing nuget package for individual VS project use vcpkg integrate powershell Enable PowerShell tab-completion vcpkg export <pkg>... [opt]... Exports a package vcpkg edit <pkg> Open up a port for editing (uses %EDITOR%, default 'code') vcpkg create <pkg> <url> [archivename] Create a new package vcpkg x-init-registry <path> Initializes a registry in the directory <path> vcpkg owns <pat> Search for files in installed packages vcpkg depend-info <pkg>... Display a list of dependencies for packages vcpkg env Creates a clean shell environment for development or compiling vcpkg version Display version information vcpkg contact Display contact information to send feedback ... 1. 내 프로젝트에서 사용 (CMake, find_package) CMakeLists.txt 에 find_package 내용 추가 CMakeLists.txt cmake_minimum_required(VERSION 3.11) project(main) set(CMAKE_CXX_STANDARD 17) add_executable(main main.cpp) if(MSVC) target_compile_options(main PRIVATE /MT) else() target_compile_options(main PRIVATE -Wall -O2) endif() find_package(fmt CONFIG REQUIRED) target_link_libraries(main PRIVATE fmt::fmt) find_package(nlohmann_json CONFIG REQUIRED) target_link_libraries(main PRIVATE nlohmann_json nlohmann_json::nlohmann_json) CMake 초기화 CMAKE_TOOLCHAIN_FILE 과 VCPKG_TARGET_TRIPLET 을 지정하여 초기화 CMAKE_TOOLCHAIN_FILE : vcpkg/scripts/buildsystems/vcpkg.cmake $ mkdir build && cd build # windows msvc $ cmake -G "Visual Studio 16 2019" -A x64 .. -DCMAKE_TOOLCHAIN_FILE=D:/Lib/vcpkg/scripts/buildsystems/vcpkg.cmake -DVCPKG_TARGET_TRIPLET=x64-windows-static # windows mingw $ cmake -G "MSYS Makefiles" .. -DCMAKE_TOOLCHAIN_FILE=D:/Lib/vcpkg/scripts/buildsystems/vcpkg.cmake -DVCPKG_TARGET_TRIPLET=x64-mingw-static # linux : VCPKG_TARGET_TRIPLET 지정안함, defualt 사용 $ cmake cmake .. -DCMAKE_TOOLCHAIN_FILE=~/lib/vcpkg/scripts/buildsystems/vcpkg.cmake Build # windows msvc : Release 모드 빌드 $ cmake --build . --config=Release # run $ Release\main.exe # mingw, linux $ make $ ./main 2. 내 프로젝트에서 사용 (라이브러리 수동으로 설정) CMake 수동 지정 : target_include_directories, target_link_directories, target_link_libraries 별도 지정 Makefile 사용 : -I -l -L 등의 옵션 추가 vcpkg/installed/triplet 디렉토리 참고 수동으로 include, lib 등 지정 사용 triplet/include : header files triplet/lib : static library triplet/bin : shared library $ tree vcpkg/installed -L 3 vcpkg/installed ├── vcpkg ... ├── x64-mingw-static │ ├── debug │ │ └── lib │ ├── include │ │ ├── benchmark │ │ ├── httplib.h │ │ ├── nlohmann │ │ ├── openssl │ │ ├── zconf.h │ │ └── zlib.h │ ├── lib │ │ ├── libbenchmark.a │ │ ├── libbenchmark_main.a │ │ ├── libcrypto.a │ │ ├── libssl.a │ │ ├── libzlib.a │ │ └── pkgconfig │ └── share │ ├── benchmark │ ├── cpp-httplib │ ├── nlohmann-json │ ├── nlohmann_json │ ├── openssl │ └── zlib ├── x64-windows │ ├── bin │ │ ├── fmt.dll │ │ └── fmt.pdb │ ├── debug │ │ ├── bin │ │ └── lib │ ├── include │ │ └── fmt │ ├── lib │ │ ├── fmt.lib │ │ └── pkgconfig │ └── share │ ├── fmt │ ├── vcpkg-cmake │ └── vcpkg-cmake-config └── x64-windows-static ├── debug │ ├── lib │ └── misc ├── include │ ├── benchmark │ ├── fmt │ ├── httplib.h │ ├── nlohmann │ ├── openssl │ ├── zconf.h │ └── zlib.h ├── lib │ ├── benchmark.lib │ ├── benchmark_main.lib │ ├── fmt.lib │ ├── libcrypto.lib │ ├── libssl.lib │ ├── ossl_static.pdb │ ├── pkgconfig │ └── zlib.lib ├── misc │ ├── CA.pl │ └── tsget.pl ├── share │ ├── benchmark │ ├── cpp-httplib │ ├── fmt │ ├── nlohmann-json │ ├── nlohmann_json │ ├── openssl │ └── zlib └── tools └── openssl

August 18, 2021 · Byung Kyu KIM

C++ REST SDK(cpprestsdk) Sample

Introduction https://github.com/Microsoft/cpprestsdk{:target="_blank"} Microsoft에서 만든 클라이언트, 서버용 C++ HTTP 통신 모듈이며, JSON URI, 비동기, 웹소켓, oAuth 등을 지원 C++11의 비동기, 병렬 프로그램 모델 지원 크로스 플랫폼 지원 등.. cpprestsdk package install (w/ vcpkg) https://github.com/microsoft/vcpkg{:target="_blank"} vcpkg 통해서 패키지 설치 # --triplet=x64-windows-static $ vcpkg.exe install cpprestsdk:x64-windows-static ... The package cpprestsdk:x64-windows-static provides CMake targets: find_package(cpprestsdk CONFIG REQUIRED) target_link_libraries(main PRIVATE cpprestsdk::cpprest cpprestsdk::cpprestsdk_zlib_internal cpprestsdk::cpprestsdk_brotli_internal) Sample code U("") 는 _T("") 와 비슷한, UNICODE 및 MBCS 환경의 문자열 타입을 스위칭 해주는 매크로. 허나 U는 _T와는 다르게 _WIN32 환경이면 기본으로 _UTF16_STRINGS으로 정의되어 있어 프로젝트의 문자집합의 세팅과 관계 없이 UNICODE와 같은 환경으로 동작 리눅스 환경에서는 다른 설정을 해주지 않는 이상 char, std::string으로 정의 utility::string_t은 std::string과 std::wstring을 스위칭 해주는 타입 대체적인 패턴은, 동기는 .get(), 비동기는 then().wait() 조합으로 사용 #include <iostream> using namespace std; #include <cpprest/http_client.h> #include <cpprest/filestream.h> using namespace utility; using namespace web; using namespace web::http; using namespace web::http::client; using namespace concurrency::streams; void HttpRequest() { http_client client(U("http://httpbin.org/get")); http_request req(methods::GET); // sync request auto resp = client.request(req).get(); wcout << resp.status_code() << " : sync request" << endl; wcout << resp.extract_string(true).get() << endl; // async request client.request(req).then([=](http_response r){ wcout << r.status_code() << " : async request" << endl; wcout << U("content-type : ") << r.headers().content_type() << endl; r.extract_string(true).then([](string_t v) { wcout << v << endl; }).wait(); }).wait(); // async request json client.request(req).then([=](http_response r){ wcout << r.status_code() << " : async request json" << endl; wcout << U("content-type : ") << r.headers().content_type() << endl; r.extract_json(true).then([](json::value v) { wcout << v << endl; }).wait(); }).wait(); } int main() { // wcout.imbue(locale("kor")); // windows only HttpRequest(); return 0; } CMakeLists.txt cmake_minimum_required(VERSION 3.11) project(main) add_executable(main main.cpp) target_compile_options(main PRIVATE /MT) find_package(cpprestsdk CONFIG REQUIRED) target_link_libraries(main PRIVATE cpprestsdk::cpprest cpprestsdk::cpprestsdk_zlib_internal cpprestsdk::cpprestsdk_brotli_internal) $ mkdir build && cd build # x64-windows-static $ cmake -G "Visual Studio 16 2019" -A x64 .. -DCMAKE_TOOLCHAIN_FILE=D:/Lib/vcpkg/scripts/buildsystems/vcpkg.cmake -DVCPKG_TARGET_TRIPLET=x64-windows-static Build & Run # build $ cmake --build . --config Release # run $ Release\main.exe 200 : sync request { "args": {}, "headers": { "Cache-Control": "max-stale=0", "Host": "httpbin.org", "User-Agent": "cpprestsdk/2.10.18", "X-Amzn-Trace-Id": "Root=1-611cbc68-27731b2a1cd55cbd682c517e", "X-Bluecoat-Via": "ce2cfae06b3f12b4" }, "origin": "xx.xx.xx.xx", "url": "http://httpbin.org/get" } 200 : async request content-type : application/json { "args": {}, "headers": { "Cache-Control": "max-stale=0", "Host": "httpbin.org", "User-Agent": "cpprestsdk/2.10.18", "X-Amzn-Trace-Id": "Root=1-611cbc68-27731b2a1cd55cbd682c517e", "X-Bluecoat-Via": "ce2cfae06b3f12b4" }, "origin": "xx.xx.xx.xx", "url": "http://httpbin.org/get" } 200 : async request json content-type : application/json {"args":{},"headers":{"Cache-Control":"max-stale=0","Host":"httpbin.org","User-Agent":"cpprestsdk/2.10.18","X-Amzn-Trace-Id":"Root=1-611cbc68-27731b2a1cd55cbd682c517e","X-Bluecoat-Via":"ce2cfae06b3f12b4"},"origin":"180.xx.xx.xx","url":"http://httpbin.org/get"}

August 17, 2021 · Byung Kyu KIM