[WordPress] Cloudflare + Kubernetes 환경에서 Real IP 얻기

Preface

최근들어 부쩍 스팸성 댓글이 활발한것 같다. WordPress에서 글이나 댓글이 작성되면, 스팸 필터링 등을 위해 작성자 IP등의 정보가 기록된다. 스팸으로 의심되는 IP나 댓글 본문은 자동으로 스팸 필터링이 적용되는데, 이 때 구축 환경 때문에 실제 IP (Real IP)가 기록되지 않는 문제가 종종 있는것 같다.

댓글이 작성되면 실제 IP가 아닌 내부 IP가 기록된다.

지금 구축된 환경에서는 사실 실제 IP(Real IP)가 직접 전달되기는 어렵다. 이를 해결하려면 끝점에 있는 WordPress에서 HTTP Header를 파싱하여 실제 IP를 가져올 필요가 있다.

Experiment #1. Cloudflare without Proxy

Cloudflare Proxy를 끄고 HTTP Request와 Header가 변형되는 과정. 물론 환경마다 다를수 있다.
직접 testbed.dailylime.dev로 테스트해볼 수 있다.

Experiment #2. Cloudflare with Proxy

Cloudflare Proxy를 켠 상태로 HTTP Request와 Header가 변형되는 과정. 물론 환경마다 다를수 있다.
직접 testbed.dailylime.dev로 테스트해볼 수 있다.

Forwarded Headers

이를 해결하기 위해서는 Header로 포워딩된 Original IP를 파싱할 필요가 있다. Cloudflare는 Origin IP를 CF-Connecting-IPX-Original-Forwarded-For 두 가지로 Forward한다. 여기서는 CF-Connecting-IP를 가지고 Origin IP를 파싱하는 방법을 사용한다.

WordPress에서의 세팅 방법은 간단하다. wp-config.php에 아래와 같이 세팅한다.

/**
 * Fixing original IP detection behind Nginx proxy
 */
if(isset($_SERVER['HTTP_CF_CONNECTING_IP'])) {
    $list = explode(',',$_SERVER['HTTP_CF_CONNECTING_IP']);
    $_SERVER['REMOTE_ADDR'] = $list[0];
}

Conclusion

결국 wp-config.php에 몇 줄만 추가되면 되는 내용인데. 사실상 정확히 알고자 하면 복잡한 부분이다. 현재 구축되어 있는 Reverse proxy에 대한 구조에 대한 이해 등이 일부 필요한 부분이 있다. 실제로 Reference [1]에서는 X-Forwarded-For를 사용하는 방법을 명시하고 있는데, Kubernetes Ingress 뒤에 있는 경우 이 값도 사실상 Internal IP이거나 Private IP일 확률이 높다. 그렇기 때문에, 정확하게 어떤 Header가 전달되는지를 확인할 필요가 있다.

아래 jungin500/http-request-tester 레포지토리는 필요한 경우 테스트 목적으로 활용 가능하다.

  • jungin500/http-request-tester:python
  • jungin500/http-request-tester:cplusplus

처음에는 Python 구현체로 만들고, 다시 C++로 변환하였다. Claude 만만세

Reference

[1] Technicus, Configure WordPress to report true IP addresses when behind a reverse proxy: https://techblog.jeppson.org/2014/09/configure-wordpress-to-report-true-ip-addresses-when-behind-a-reverse-proxy/

[2] Cloudflare Docs, Restoring original visitor IPs: https://developers.cloudflare.com/support/troubleshooting/restoring-visitor-ips/restoring-original-visitor-ips/#nginx-1

[3] Cloudflare, IP Ranges: https://www.cloudflare.com/ko-kr/ips/

[Kubernetes] PyTorch 학습 시 Pod의 빠른 종료를 위한 yaml 설계 방법

[새로운 방법 발견!]

아래 방법을 계속 사용하다가, yaml에 직접 넣어서 사용할 수 있는 구문을 찾았습니다.

spec:
  terminationGracePeriodSeconds: 0

해당 구문을 이용하여 Pod delete시 바로 중단 및 삭제되도록 할 수 있습니다.


기존 방법으로는 kubectl delete 시 --force --grace-period=0 옵션을 주어야만 강제 종료되고, 학습 process에 실제로 Ctrl+C를 주는 것과 동일하게 SIGTERM 을 보낼 수는 없었습니다. 이러한 문제점은 학습 프로세스의 종료시 callback들 (wandb 등)이 정상 작동하지 않는다는 문제점이 있습니다.이를 해결할 수 있는 방안을 소개 드립니다.
다만 아래와 같은 몇 가지 drawback이 있으므로 참고하여주시고, 더 좋은 방법이 있다면 공유 부탁드립니다.

  1. pip install 이 불가능하므로 미리 requirements.txt를 설치한 image를 준비해야 함
  2. runAsUserrunAsGroup 을 1003으로 고정해야 하므로 HOME 변수를 /workspace로 고정해야만 사용 가능

기존 방식

apiVersion: v1
kind: Pod
metadata:
  name: jungin500-mobilenetv2
spec:
  securityContext:
    runAsUser: 0
    runAsGroup: 0
    fsGroup: 1003

  restartPolicy: Never

  volumes:
    - name: shmdir
      emptyDir:
        medium: Memory
    - name: pvc-volume
      persistentVolumeClaim:
        claimName: lab-pvc

  containers:
    - name: gpu-container
      image: ghcr.io/jungin500/mobilenet_v2
      volumeMounts:
        - mountPath: /dev/shm
          name: shmdir
        - mountPath: /home/lab
          name: pvc-volume
      env:
        - name: TZ
          value: Asia/Seoul
      command:
        - "/bin/sh"
        - "-c"
      args:
        - >-
          set -x &&
          groupadd -g 1003 lab &&
          useradd -m -d /workspace -s /bin/bash -u 1003 -g lab lab &&
          runuser -u lab -- git clone https://jungin500:*****@github.com/jungin500/mobilenet_v2 mobilenet_v2 &&
          cd /workspace/mobilenet_v2 &&
          runuser -u lab -- git checkout 7d198633d19c2005e22b118ba27082eca3f2846a &&
          runuser -u lab -- pip3 install -r requirements.txt &&
          runuser -u lab -- /bin/bash -c "mkdir -p /home/lab/jungin500/mobilenet_v2_220718 || true" &&
          runuser -u lab -- python3 train.py ****
      securityContext:
        allowPrivilegeEscalation: false

      resources:
        requests:
          nvidia.com/gpu: 1
        limits:
          nvidia.com/gpu: 1

변경된 방식

apiVersion: v1
kind: Pod
metadata:
  name: jungin500-shutdown-signal-test
spec:
  securityContext:
    # [1] runAsUser, runAsGroup을 Fix
    runAsUser: 1003
    runAsGroup: 1003
    fsGroup: 1003

  restartPolicy: Never

  volumes:
    - name: shmdir
      emptyDir:
        medium: Memory
    - name: workdir
      emptyDir: {}
    - name: pvc-volume
      persistentVolumeClaim:
        claimName: lab-pvc

  # [2] git clone, 학습 결과물 폴더 링크 세팅등을 initContainers에서 진행
  # 이 때, pip install 등은 불가능하므로 미리 requirements.txt를 설치한 image를 준비해야 함
  initContainers:
    - name: clone-directory-set
      image: alpine/git
      volumeMounts:
        - mountPath: /workspace
          name: workdir
        - mountPath: /home/lab
          name: pvc-volume
      workingDir: /workspace
      env:
        - name: TZ
          value: Asia/Seoul
        - name: HOME
          value: /workspace
      command:
        - "/bin/sh"
        - "-c"
      args:
        - >-
          set -x &&
          git clone https://jungin500:***@github.com/jungin500/mobilenet_v2 mobilenet_v2 &&
          cd /workspace/mobilenet_v2 &&
          git checkout 7d198633d19c2005e22b118ba27082eca3f2846a &&
          mkdir -p /home/lab/jungin500/mobilenet_v2_test || true
  
  # [3] 기타 작업 (폴더 생성, 이동 등)은 불가능함
  #     argument도 string의 형태가 아닌 array로 주어야 작동함
  containers:
    - name: gpu-container
      image: ghcr.io/jungin500/mobilenet_v2
      volumeMounts:
        - mountPath: /dev/shm
          name: shmdir
        - mountPath: /workspace
          name: workdir
        - mountPath: /home/lab
          name: pvc-volume
      workingDir: /workspace/mobilenet_v2
      env:
        - name: TZ
          value: Asia/Seoul
        - name: HOME
          value: /workspace
      command:
        - "/opt/conda/bin/python3.8"
        - "train.py"
      args:
        - "--arg1"
        - "arg1_value"
      securityContext:
        allowPrivilegeEscalation: false

      resources:
        requests:
          nvidia.com/gpu: 1
        limits:
          nvidia.com/gpu: 1

구체적으로 변경되어야 하는 부분은 다음과 같습니다.

spec.securityContext.runAsUser
spec.securityContext.runAsGroup
spec.volumes.name[workdir]
spec.initContainers
spec.containers.volumeMounts[mountPath=/workspace]
spec.containers.env[name=HOME]
spec.containers.command
spec.containers.args

[DSM 7.0] Synology DSM Docker에서 Docker-in-Docker (dind) 실행하기

서론

Docker-in-Docker는 이미 존재하는 Docker Daemon에서 새로운 Container를 구동하고, 그 안에서 새로운 Daemon을 구동하는 기법이다.

기존에는 docker:dind 이미지와 --privileged 플래그를 이용하여 새로운 컨테이너를 생성하면 바로 가능한 간단한 문제였으나, Synology DSM 7.0에서는 기본 dockerstorage-driveraufs로 설정되어 있고 overlay2 드라이버를 지원하지 않으므로 이러한 기본적인 접근방식은 불가능하였다.

해결 방법

기존에는 아래와 같이 dind 컨테이너를 생성하였다.

docker run \
   --name jenkins-docker \
   --rm \
   --detach \
   --privileged \
   --network jenkins \
   --network-alias docker \
   --env DOCKER_TLS_CERTDIR=/certs \
   --volume jenkins-docker-certs:/certs/client \
   --volume jenkins-data:/var/jenkins_home \
   --publish 2376:2376 \
   docker:dind \
   --storage-driver overlay2

위 명령어는 jenkins 컨테이너를 위한 dind 컨테이너 생성 명령어(링크)다. 이 마지막 부분에 보면 --storage-driver 인자가 있는데, 이 부분만 aufs로 바꿔주면 바로 문제가 해결된다.

docker run \
   --name jenkins-docker \
   --rm \
   --detach \
   --privileged \
   --network jenkins \
   --network-alias docker \
   --env DOCKER_TLS_CERTDIR=/certs \
   --volume jenkins-docker-certs:/certs/client \
   --volume jenkins-data:/var/jenkins_home \
   --publish 2376:2376 \
   docker:dind \
   --storage-driver aufs

[해결됨] WSL2 CUDA undefined symbol: devicesetgpcclkvfoffset 문제 해결하기

[추가] 현재는 Fix된 이슈임

Windows 11 Insider Preview Build 22000.51이 나온 뒤에는 해결된 문제입니다. 아래 환경에서 테스트하였으니 apt 패키지와 드라이버를 업데이트 해보시기 바랍니다.

  • OS: Windows 11 Insider Preview Build 22000.51
  • Driver: NVIDIA 470.76
  • APT Package Version List
Inst libnvidia-container1 (1.4.0-1 NVIDIA CORPORATION [email protected]:1.0/bionic [amd64])
 Inst libnvidia-container-tools (1.4.0-1 NVIDIA CORPORATION [email protected]:1.0/bionic [amd64])
 Inst nvidia-container-toolkit (1.5.1-1 NVIDIA CORPORATION [email protected]:1.0/bionic [amd64])
 Inst nvidia-container-runtime (3.5.0-1 NVIDIA CORPORATION [email protected]:1.0/bionic [amd64])
 Inst nvidia-docker2 (2.6.0-1 NVIDIA CORPORATION [email protected]:1.0/bionic [all])
 Conf libnvidia-container1 (1.4.0-1 NVIDIA CORPORATION [email protected]:1.0/bionic [amd64])
 Conf libnvidia-container-tools (1.4.0-1 NVIDIA CORPORATION [email protected]:1.0/bionic [amd64])
 Conf nvidia-container-toolkit (1.5.1-1 NVIDIA CORPORATION [email protected]:1.0/bionic [amd64])
 Conf nvidia-container-runtime (3.5.0-1 NVIDIA CORPORATION [email protected]:1.0/bionic [amd64])
 Conf nvidia-docker2 (2.6.0-1 NVIDIA CORPORATION [email protected]:1.0/bionic [all])

Environment: Windows 10 Insider Preview Build 21376.1
WSL2 Ubuntu release: 20.04
NVIDIA Forum Links: https://forums.developer.nvidia.com/t/nvidia-container-cli-error/177403/2?u=ji5489

문제 제기

if I run sudo nvidia-container-cli -k -d /dev/tty info

I got this error
where is ‘devicesetgpcclkvfoffset’ symbol?

– WARNING, the following logs are for debugging purposes only –
I0509 06:20:58.858216 1009 nvc.c:372] initializing library context (version=1.4.0, build=704a698b7a0ceec07a48e56c37365c741718c2df)
I0509 06:20:58.858281 1009 nvc.c:346] using root /
I0509 06:20:58.858287 1009 nvc.c:347] using ldcache /etc/ld.so.cache
I0509 06:20:58.858293 1009 nvc.c:348] using unprivileged user 65534:65534
I0509 06:20:58.858311 1009 nvc.c:389] attempting to load dxcore to see if we are running under Windows Subsystem for Linux (WSL)
I0509 06:20:58.891385 1009 dxcore.c:226] Creating a new WDDM Adapter for hAdapter:40000000 luid:1e946dc
I0509 06:20:58.917427 1009 dxcore.c:267] Adding new adapter via dxcore hAdapter:40000000 luid:1e946dc wddm version:3000
I0509 06:20:58.917515 1009 dxcore.c:325] dxcore layer initialized successfully
W0509 06:20:58.918854 1009 nvc.c:397] skipping kernel modules load on WSL
I0509 06:20:58.919404 1010 driver.c:101] starting driver service
E0509 06:20:58.950931 1010 driver.c:168] could not start driver service: load library failed: /usr/lib/wsl/drivers/nv_dispi.inf_amd64_43efafcd74b2efc9/libnvidia-ml.so.1: undefined symbol: devicesetgpcclkvfoffset
I0509 06:20:58.951399 1009 driver.c:203] driver service terminated successfully
nvidia-container-cli: initialization error: driver error: failed to process request

해결방법

I’m currently installing WSL2 Ubuntu 20.04 within Windows 10 Insider Preview Build 21376.1, and faced same issue like below.

# sudo nvidia-container-cli -k -d /dev/tty info

-- WARNING, the following logs are for debugging purposes only --

I0512 07:05:58.485519 5592 nvc.c:372] initializing library context (version=1.4.0, build=704a698b7a0ceec07a48e56c37365c741718c2df)
I0512 07:05:58.485581 5592 nvc.c:346] using root /
I0512 07:05:58.485601 5592 nvc.c:347] using ldcache /etc/ld.so.cache
I0512 07:05:58.485604 5592 nvc.c:348] using unprivileged user 65534:65534
I0512 07:05:58.485659 5592 nvc.c:389] attempting to load dxcore to see if we are running under Windows Subsystem for Linux (WSL)
I0512 07:05:58.502183 5592 dxcore.c:226] Creating a new WDDM Adapter for hAdapter:40000000 luid:185673b
I0512 07:05:58.512924 5592 dxcore.c:267] Adding new adapter via dxcore hAdapter:40000000 luid:185673b wddm version:3000
I0512 07:05:58.512956 5592 dxcore.c:325] dxcore layer initialized successfully
W0512 07:05:58.513266 5592 nvc.c:397] skipping kernel modules load on WSL
I0512 07:05:58.513404 5593 driver.c:101] starting driver service
E0512 07:05:58.521931 5593 driver.c:168] could not start driver service: load library failed: /usr/lib/wsl/drivers/nv_dispi.inf_amd64_43efafcd74b2efc9/libnvidia-ml.so.1: undefined symbol: devicesetgpcclkvfoffset
I0512 07:05:58.522047 5592 driver.c:203] driver service terminated successfully
nvidia-container-cli: initialization error: driver error: failed to process request

and I found out that apt-get experimental repository and stable one is mixed out – failing to install WSL2 one (which is available in experimental repository). as stable package is released, experimental(=WSL2) package should be released, but It wasn’t. see apt-cache madison result below.

# apt-cache madison libnvidia-container1
libnvidia-container1 |    1.4.0-1 | https://nvidia.github.io/libnvidia-container/stable/ubuntu18.04/amd64  Packages
libnvidia-container1 |    1.3.3-1 | https://nvidia.github.io/libnvidia-container/stable/ubuntu18.04/amd64  Packages
libnvidia-container1 | 1.3.3~rc.2-1 | https://nvidia.github.io/libnvidia-container/experimental/ubuntu18.04/amd64  Packages
libnvidia-container1 | 1.3.3~rc.1-1 | https://nvidia.github.io/libnvidia-container/experimental/ubuntu18.04/amd64  Packages
libnvidia-container1 |    1.3.2-1 | https://nvidia.github.io/libnvidia-container/stable/ubuntu18.04/amd64  Packages
libnvidia-container1 |    1.3.1-1 | https://nvidia.github.io/libnvidia-container/stable/ubuntu18.04/amd64  Packages

The point is, we should install libnvidia-container1=1.3.3~rc.2-1 version rather than libnvidia-container1=1.4.0-1. but normal apt-get install nvidia-docker2 command would install 1.4.0-1 version, and It mostly like to fail in WSL2 environment.

I successfully installed older (WSL2-exclusive) packages via apt-get install command below:

apt-get install \
    libnvidia-container1=1.3.3~rc.2-1 \
    libnvidia-container-tools=1.3.3~rc.2-1 \
    nvidia-container-toolkit=1.4.1-1 \
    nvidia-container-runtime=3.4.1-1 \
    nvidia-docker2=2.5.0-1

Those commands will install older packages, and after sudo service docker stop and sudo service docker start, CUDA will work inside docker.

[튜토리얼] Docker로 apt-mirror 미러서버를 구축해보자

결과 확인해보기: https://mirror.limenas.ml

미러 서버는 , 데비안 계열 리눅스에서(Debian, Ubuntu),
시스템에 설치할 수 있는 deb 패키지들을 가지고 있는 서버이며,
이 서버에 빠르게 접근할 수 있도록 서버를 통째로 복제해둔 로컬 서버입니다.

Raspberry PiJetson Nano와 같은 SBC(Single Board Computer)를 사용하다 보면, 같은 Ubuntu/Debian 계열 Linux임에도 불구하고, CPU 아키텍쳐가 ARM이라는 이유로 카카오에서 제공하는 빠른 미러서버를 사용하기 어려워집니다.(이 미러서버에는 ARM 아키텍쳐의 바이너리들을 미러링을 하지 않습니다!) 저는 주로 한국에서 가장 빠른 mirror.kakao.com를 주 미러 서버로 사용하는데, 위의 문제 때문에 카카오 미러서버는 PC나 워크스테이션에만 한정하여 사용합니다.

사실 ports.ubuntu.com 라는 곳에서, 우분투 (반)공식으로 비-인텔 CPU(ARM, ARM64, MIPS 등등)에서 사용할 수 있는 패키지를 배포하긴 합니다. 다만, 서버는 영국에 있어서 경우에 따라서는 매우 느려서 속이 터집니다(한국인).

개인적으로, 라즈베리파이와 Jetson Nano를 모두 사용하고 있고, 연구 목적으로도 사용하고 있어서, 미러 서버를 구축하게 되었습니다.

1단계: apt-mirror-downloader Docker 이미지를 만들어보자

이 튜토리얼에서는 도커를 이용해서, 미러를 수행하는 Downloader를 실행합니다. 아래 Dockerfile을 이용해서 도커 이미지를 생성할 수 있습니다.

Dockerfile이라는 이름(확장자 없음)의 파일을 생성하여, 아래 내용을 저장합니다.

FROM ubuntu:latest

RUN sed -i "s|archive.ubuntu.com|mirror.kakao.com|g" /etc/apt/sources.list &&\
    apt -qq update && apt -y --no-install-recommends -qq install wget curl git make ca-certificates &&\
    rm -rf /var/lib/apt/lists

RUN git clone https://github.com/Stifler6996/apt-mirror.git && cd apt-mirror &&\
    make install && cd .. && rm -rf apt-mirror

ENTRYPOINT apt-mirror

위 파일을 저장한 뒤, 아래 명령어를 실행하여 이미지를 빌드합니다 (물론 이미지 이름이나 태그는 원하는 것으로 변경하면 됩니다).

Ubuntu에서 패키지로 배포하는 apt-mirror의 경우 c-n-f(Content-Not-Found)나 dep11(Dependency 관련)과 같은 특수 태그를 지원하지 않습니다. 이 튜토리얼에서는, 해당 최신 태그를 지원하도록 패치한 apt-mirror 버전인 Stifler6996/apt-mirror를 사용하여 진행합니다.

docker build . -t jungin500/apt-mirror:arm64

이미지를 만들었다면, 이제 미러링 설정 파일을 생성해줍니다. 어떤 사이트를 미러링할지, 쓰레드 수는 얼마나 줄 것인지 등을 설정하는 과정입니다. mirror.list라는 파일을 새로 만들어, 아래 내용을 저장합니다.

####### config
#
set base_path    /var/spool/apt-mirror
#
#set mirror_path  $base_path/mirror
#set skel_path    $base_path/skel
#set var_path     $base_path/var
#set cleanscript $var_path/clean.sh
#set defaultarch  
#set postmirror_script $var_path/postmirror.sh
#set run_postmirror 0
set nthreads     20
#set _tilde 0
#
####### end config

# Begin Raspberry Pi (Debian 10) ARM32/ARM64 configuration
deb [arch=armhf,arm64] http://archive.raspberrypi.org/debian buster main
# deb-src http://archive.raspbian.org/debian buster main
# End Raspberry Pi (Debian 10) ARM32/ARM64 configuration

위쪽 config 파트에서는 디렉토리나 thread수를 결정할 수 있습니다. 이 뒤부터는 보통 사용하는 sources.list와 동일합니다. 다만, 아키텍쳐를 [arch=armhf,arm64] 지시어로 지정합니다. 여기서는 armhf(32비트 ARM Hard Float)와 arm64(64비트 ARM) 두 가지 아키텍쳐에 해당하는 패키지만 다운로드한다는 의미입니다.

이런 식으로, 추가로 mirror.kakao.com나 ftp.kr.debian.org 등의 미러링이 가능합니다. 사용하고 있는 배포판에서 /etc/apt/sources.list를 뜯어서, 그 내용을 그대로 이 파일의 맨 아래에 넣어주면 됩니다. 다만, 아키텍쳐는 기본이 amd64로 지정되므로 위 내용 [arch=armhf,arm64]와 같이 explicit하게 지정해줘야 합니다!

다음으로는 두 번째 설정 파일입니다. 이 스크립트는 미러링이 끝난 뒤 ls-lR.gz 파일을 생성합니다. apt-get으로 패키지 메타데이터를 다운로드하게 되는데, ls-lR.gz는 이 때 필요한 파일입니다. 아래 스크립트를 postmirror.sh 라는 파일로 저장합니다.

#!/bin/bash
# ls-lR Creator Postscript for apt-mirror
# LimeOrangePie [email protected]

MIRROR_ROOT=/var/spool/apt-mirror
cd $MIRROR_ROOT/mirror

IFS=$'\n'
MIRRORS=( $(ls -1) )

for mirror_item in "${MIRRORS[@]}"
do
    cd $MIRROR_ROOT/mirror/$mirror_item
    DISTRIBUTIONS=( $(ls -1) )

    for dist_name in "${DISTRIBUTIONS[@]}"
    do
        cd $MIRROR_ROOT/mirror/$mirror_item/$dist_name
        rm -f ls-lR.gz
        ls -lR > ls-lR
        gzip ls-lR
    done
done

위 두 파일을 준비했다면, 다음으로, 만든 이미지를 이용해서 미러링을 수행합니다. 미러링을 할 디렉토리는 300GB 이상의 여유 공간이 있는 것이 좋습니다. 4개 서버를 미러링했더니 500GB정도가 나오네요. STORAGE_PATH를 변경하여 미러링할 대상 폴더를 지정해주세요.

DOCKER_WORKDIR=pwd
STORAGE_PATH=/mirror-storage
docker run \
         -it \
         --name apt-mirror-downloader \
         -v $DOCKER_WORKDIR/mirror.list:/etc/apt/mirror.list:ro \
         -v $DOCKER_WORKDIR/postmirror.sh:/var/spool/apt-mirror/var/postmirror.sh:ro \
         -v $STORAGE_PATH:/var/spool/apt-mirror:rw \
         --entrypoint apt-mirror \
         --rm \
         jungin500/apt-mirror:arm64

미러링은 3시간에서, 길면 반나절까지 걸립니다. 백그라운드로 돌리려면 docker 명령어에 -d 플래그를 붙여두고 기다리시면 됩니다.

다음 게시물에서는 만든 미러서버를 제공(Serve)하는 방법을 소개해 드리겠습니다. 지금까지 미러링한 서버를 실제로 다른 사람들이 쓸 수 있도록 간단한 웹 서버를 만들어서 배포합니다.

[Tutorial] Building lastest raspberry pi kernel for 64-bit Ubuntu (20.10)

One of the great parts about running Ubuntu is that just about all the Ubuntu-isms you’ve learned for other platforms work here too. Start with these links:

https://wiki.ubuntu.com/Kernel/BuildYourOwnKernel
https://wiki.ubuntu.com/KernelTeam/ARMK … ossCompile
https://wiki.ubuntu.com/KernelTeam/Kern … k_failures
https://askubuntu.com/questions/500095/ … er-version
https://bugs.launchpad.net/ubuntu/+sour … ug/1701756

What follows isn’t very polished, since came out of my notebook verbatim. This is how I built the kernel.

First uncomment the relevant line int /etc/apt/sources.list:

deb-src http://ports.ubuntu.com/ubuntu-ports focal-updates main restricted

Update the package database:

apt update

Get the kernel source package, as root in some place where you want it. Alternatively replace $(uname -r) with the version you want. This is probably easiest to do on the target:

apt-get source linux-image-$(uname -r)

If this is on a target, copy it to a dev machine.

Over on the dev machine, hack up your kernel as you please. Then in debian.raspi/changelog, edit the first version number from something like this:

linux-raspi (5.4.0-1019.21) focal; urgency=medium

to something like this:

linux-raspi (5.4.0-1019.21+g34950~20200925) focal; urgency=medium

Note that CONFIG_LOCALVERSION will break the Ubuntu scripts, and EXTRAVERSION in the highest level makefile doesn’t do anything interesting.

Set some environment variables:

export $(dpkg-architecture -aarm64); export CROSS_COMPILE=aarch64-linux-gnu-

Now change into the root directory of the source tree and clean the build area:

fakeroot debian/rules clean

Kick off a menuconfig session with script:

fakeroot debian/rules editconfigs

menuconfig insists on running once each for 32 and 64 bit builds of kernel.

Now build the kernel and associated packages. We skip checks that are likely to break because of a changed list of modules:

fakeroot debian/rules binary skipmodule=true skipabi=true

This will result in the following .deb packages being created in the level ABOVE the kernel source tree:

linux-buildinfo-5.4.0-1019-raspi_5.4.0-1019.21+g34950~20200925_arm64.deb
linux-headers-5.4.0-1019-raspi_5.4.0-1019.21+g34950~20200925_arm64.deb
linux-image-5.4.0-1019-raspi_5.4.0-1019.21+g34950~20200925_arm64.deb
linux-modules-5.4.0-1019-raspi_5.4.0-1019.21+g34950~20200925_arm64.deb
linux-raspi-headers-5.4.0-1019_5.4.0-1019.21+g34950~20200925_arm64.deb

After copying to the target, each of the relevant packages may be installed there with dpkg:

dpkg -i linux-headers-5.4.0-1019-raspi_5.4.0-1019.21+g34950~20200925_arm64.deb
dpkg -i linux-image-5.4.0-1019-raspi_5.4.0-1019.21+g34950~20200925_arm64.deb
dpkg -i linux-modules-5.4.0-1019-raspi_5.4.0-1019.21+g34950~20200925_arm64.deb
dpkg -i linux-raspi-headers-5.4.0-1019_5.4.0-1019.21+g34950~20200925_arm64.deb

[TEST] Tensorflow 2.4.0-rc0 on RTX 3000 series (3070/3080/3090)

Tensorflow on RTX 3000 series (RTX 3070, RTX 3080, RTX 3090)

빌드 환경 (Build environment)

OS: Windows 10 Education (Build 19042.608)
Architecture: x86_64 (amd64)
Git branch: v2.4.0-rc0
Python: 3.7 (anaconda)
Target CUDA and CUDNN: CUDA 11.1 Update 1, CUDNN v8.0.5 (Novemvber 9th, 2020) (requires login)
Target arch: CC 8.6, 6.1 → Must be also usable on GTX 1000 series!
Numpy: 1.19.4 (Must be manually reinstalled back to version 1.19.3 before using!)

사용법 (Usage)

  1. Requirements: CUDA 11.1 Update 1, CUDNN v8.0.5 (Novemvber 9th, 2020) (requires login)
  2. Download tensorflow-2.4.0rc0-cp37-cp37m-win_amd64.whl
  3. Install within CMD or Powershell cmdline (where pip3 is available)
  4. Install tensorflow : pip install tensorflow-2.4.0rc0-cp37-cp37m-win_amd64.whl
  5. (Optional) Install additional requirements
  6. (Required) Roll back numpy version to 1.19.3: pip install numpy==1.19.3
  7. (Maybe optional) cupti library filename mismatch – add “C:\Program Files\NVIDIA GPU Computing Toolkit\CUDA\v11.1\extras\CUPTI\lib64” to PATH and copy “cupti64_2020.2.1.dll” to “cupti64.dll” or “cupti.dll”.

제한 사항 (Restriction, To-Dos)

  • Higher GPU usage might be restricted – use those code to resolve SOME of those problems:
# Memory Pre-configuration
config = tf.compat.v1.ConfigProto(
    gpu_options=tf.compat.v1.GPUOptions(
        per_process_gpu_memory_fraction=0.8,
        allow_growth = True
    )
    # device_count = {'GPU': 1}
)
session = tf.compat.v1.Session(config=config)
tf.compat.v1.keras.backend.set_session(session)
  • Closing application while tensorflow library loads always failes – might be a buggy codes?
  • another unknown restriction would exist – this is a test build for my own use, so use with care! I will edit this article when tensorflow officially supports RTX3000 series (or tested).