<kbd id="afajh"><form id="afajh"></form></kbd>
<strong id="afajh"><dl id="afajh"></dl></strong>
    <del id="afajh"><form id="afajh"></form></del>
        1. <th id="afajh"><progress id="afajh"></progress></th>
          <b id="afajh"><abbr id="afajh"></abbr></b>
          <th id="afajh"><progress id="afajh"></progress></th>

          kubelet 遠(yuǎn)程調(diào)試方法

          共 9620字,需瀏覽 20分鐘

           ·

          2022-07-22 15:42

          1. kubelet啟動(dòng)命令分析

          kubelet是一個(gè)systemd服務(wù),以使用Kubeadm工具安裝的v1.23.4 k8s集群為例,該服務(wù)的配置文件路徑為/etc/systemd/system/kubelet.service.d/10-kubeadm.conf, 內(nèi)容如下:

          # Note: This dropin only works with kubeadm and kubelet v1.11+
          [Service]
          Environment="KUBELET_KUBECONFIG_ARGS=--bootstrap-kubeconfig=/etc/kubernetes/bootstrap-kubelet.conf --kubeconfig=/etc/kubernetes/kubelet.conf"
          Environment="KUBELET_CONFIG_ARGS=--config=/var/lib/kubelet/config.yaml"
          # This is a file that "kubeadm init" and "kubeadm join" generates at runtime, populating the KUBELET_KUBEADM_ARGS variable dynamically
          EnvironmentFile=-/var/lib/kubelet/kubeadm-flags.env
          # This is a file that the user can use for overrides of the kubelet args as a last resort. Preferably, the user should use
          # the .NodeRegistration.KubeletExtraArgs object in the configuration files instead. KUBELET_EXTRA_ARGS should be sourced from this file.
          EnvironmentFile=-/etc/default/kubelet
          ExecStart=
          ExecStart=/usr/bin/kubelet $KUBELET_KUBECONFIG_ARGS $KUBELET_CONFIG_ARGS $KUBELET_KUBEADM_ARGS $KUBELET_EXTRA_ARGS

          以我的測(cè)試環(huán)境為例,執(zhí)行ps -ef |grep /usr/bin/kubelet, 可見kubelet啟動(dòng)的完整命令如下:

          /usr/bin/kubelet --bootstrap-kubeconfig=/etc/kubernetes/bootstrap-kubelet.conf --kubeconfig=/etc/kubernetes/kubelet.conf --config=/var/lib/kubelet/config.yaml --container-runtime=remote --container-runtime-endpoint=/run/containerd/containerd.sock --pod-infra-container-image=k8s.gcr.io/pause:3.6

          如果需要修改kubelet命令,可以關(guān)閉服務(wù)后使用相同參數(shù)啟動(dòng)。或修改systemd配置文件后重啟kubelet服務(wù)。

          2. 編譯kubelet

          根據(jù)k8s makefile 源碼分析[1],kubelet編譯命令如下:

          https://github.com/kubernetes/kubernetes/blob/v1.22.4/hack/lib/golang.sh#L679

          kube::golang::build_some_binaries() {
              ...
              go install "${build_args[@]}" "$@"
              ...
          }

          其中GOLDFLAGS, GOGCFLAGS配置如下:

          https://github.com/kubernetes/kubernetes/blob/v1.22.4/hack/lib/golang.sh#L797-L799

          kube::golang::build_binaries() {
              ...
              goldflags="${GOLDFLAGS=-s -w} $(kube::version::ldflags)"
              goasmflags="-trimpath=${KUBE_ROOT}"
              gogcflags="${GOGCFLAGS:-} -trimpath=${KUBE_ROOT}"
              ...
          }

          為了保留盡可能多的調(diào)試信息,我們需要重新設(shè)置這兩個(gè)編譯參數(shù),所以編譯kubelet的命令應(yīng)為

          git clone https://github.com/kubernetes/kubernetes.git
          cd kubernetes
          git checkout v1.22.4
          ./build/shell.sh
          make generated_files
          make -o generated_files kubelet KUBE_BUILD_PLATFORMS=linux/amd64 GOLDFLAGS="" GOGCFLAGS="all=-N -l"

          編譯完成后,kubelet二進(jìn)制文件位于_output/bin/kubelet

          3. delve介紹

          delve[2]是一個(gè)用于Go編程語言的調(diào)試器。盡管我們也可以使用gdb調(diào)試go語言程序[3], 但在調(diào)試用標(biāo)準(zhǔn)工具鏈構(gòu)建的Go程序時(shí),Delve是GDB更好的替代品。它比GDB更能理解Go的運(yùn)行時(shí)、數(shù)據(jù)結(jié)構(gòu)和表達(dá)式。

          可以使用如下命令安裝dlv:

          go install github.com/go-delve/delve/cmd/dlv@latest

          使用如下命令使用dlv進(jìn)行調(diào)試:

          dlv exec ./hello -- server --config conf/config.toml

          以kubelet為例,使用dlv命令行調(diào)試的過程如下:

          root@st0n3-host:~# dlv exec /usr/bin/kubelet -- --bootstrap-kubeconfig=/etc/kubernetes/bootstrap-kubelet.conf --kubeconfig=/etc/kubernetes/kubelet.conf --config=/var/lib/kubelet/config.yaml --container-runtime=remote --container-runtime-endpoint=/run/containerd/containerd.sock --pod-infra-container-image=k8s.gcr.io/pause:3.6
          Type 'help' for list of commands.
          (dlv) b main.main
          Breakpoint 1 set at 0x502e086 for main.main() _output/dockerized./cmd/kubelet/kubelet.go:39
          (dlv) c
          > main.main() _output/dockerized./cmd/kubelet/kubelet.go:39 (hits goroutine(1):1 total:1) (PC: 0x502e086)
              34:  _ "k8s.io/component-base/metrics/prometheus/restclient"
              35:  _ "k8s.io/component-base/metrics/prometheus/version" // for version metric registration
              36:  "k8s.io/kubernetes/cmd/kubelet/app"
              37: )
              38: 
          =>  39: func main() {
              40:  command := app.NewKubeletCommand()
              41: 
              42:  // kubelet uses a config file and does its own special
              43:  // parsing of flags and that config file. It initializes
              44:  // logging after it is done with that. Therefore it does
          (dlv) 

          4. GoLand遠(yuǎn)程調(diào)試kubelet

          我們當(dāng)然可以使用上文描述的命令行形式進(jìn)行調(diào)試,但kubernetes代碼量巨大,使用IDE會(huì)更方便。

          點(diǎn)擊調(diào)試按鈕左側(cè)的Edit Configurations按鈕,配置dlv的地址和端口:

          img

          使用IDE提示的命令啟動(dòng)kubelet,或?qū)⑵渑渲玫絪ystemd服務(wù)中后重啟服務(wù):

          root@st0n3-host:~# cat /etc/systemd/system/kubelet.service.d/10-kubeadm.conf 
          ...
          ExecStart=/usr/bin/dlv --listen=:10086 --headless=true --api-version=2 --accept-multiclient exec /usr/bin/kubelet -- $KUBELET_KUBECONFIG_ARGS $KUBELET_CONFIG_ARGS $KUBELET_KUBEADM_ARGS $KUBELET_EXTRA_ARGS
          root@st0n3-host:~# systemctl daemon-reload
          root@st0n3-host:~# systemctl restart kubelet.service

          此時(shí)kubelet命令實(shí)際還未真正啟動(dòng),在GoLand中運(yùn)行剛剛添加的配置,連接上dlv后,kubelet才會(huì)運(yùn)行。

          下好斷點(diǎn),點(diǎn)擊debug按鈕,我們就可以在IDE中對(duì)kubelet進(jìn)行調(diào)試了。

          5. 其他容器軟件調(diào)試命令

          5.1 runc

          編譯

          make shell
          make EXTRA_FLAGS='-gcflags="all=-N -l"'

          調(diào)試

          mv /usr/bin/runc /usr/bin/runc.bak
          cat <<EOF > /usr/bin/runc
          #!/bin/bash
          dlv --listen=:2345 --headless=true --api-version=2 --accept-multiclient exec /usr/bin/runc.debug -- $*
          chmod +x /usr/bin/runc

          5.2 docker-cli

          編譯

          修改scripts/build/binary中的編譯命令如下:刪除LDFLAGS,添加gcflags

          root@st0n3:~/cli# git diff
          diff --git a/scripts/build/binary b/scripts/build/binary
          index e4c5e12a6b..155528e501 100755
          --- a/scripts/build/binary
          +++ b/scripts/build/binary
          @@ -74,7 +74,7 @@ fi
           echo "Building $GO_LINKMODE $(basename "${TARGET}")"
           
           export GO111MODULE=auto
          -
          -go build -o "${TARGET}" -tags "${GO_BUILDTAGS}" --ldflags "${LDFLAGS}" ${GO_BUILDMODE} "${SOURCE}"
          +go build -o "${TARGET}" -tags "${GO_BUILDTAGS}" -gcflags="all=-N -l" ${GO_BUILDMODE} "${SOURCE}"
           
           ln -sf "$(basename "${TARGET}")" "$(dirname "${TARGET}")/docker"
          make -f docker.Makefile shell
          make binary

          調(diào)試

          cat <<EOF > docker.debug
          #!/bin/bash
          dlv --listen=:2344 --headless=true --api-version=2 --accept-multiclient exec ./docker-cli.debug -- $*
          chmod +x docker.debug

          5.3 dockerd

          編譯

          修改hack/make/.binary文件中的編譯命令

          root@st0n3:~/moby# git diff
          diff --git a/hack/make/.binary b/hack/make/.binary
          index d56e3f3126..3e23865c81 100644
          --- a/hack/make/.binary
          +++ b/hack/make/.binary
          @@ -81,11 +81,11 @@ hash_files() {
           
                  echo "Building: $DEST/$BINARY_FULLNAME"
                  echo "GOOS=\"${GOOS}\" GOARCH=\"${GOARCH}\" GOARM=\"${GOARM}\""
          -       go build \
          +       set -x
          +       go build -gcflags "all=-N -l"  \
                          -o "$DEST/$BINARY_FULLNAME" \
                          "${BUILDFLAGS[@]}" \
                          -ldflags "
          -               $LDFLAGS
                          $LDFLAGS_STATIC_DOCKER
                          $DOCKER_LDFLAGS
                  " \
          make BIND_DIR=. shell
          hack/make.sh binary

          調(diào)試

          /root/go/bin/dlv --listen=:2343 --headless=true --api-version=2 --accept-multiclient exec /usr/bin/dockerd.debug -- -D -H unix:///var/run/docker.sock --containerd=/run/containerd/containerd.sock

          原文地址:https://ssst0n3.github.io/post/%E7%BD%91%E7%BB%9C%E5%AE%89%E5%85%A8/%E5%AE%89%E5%85%A8%E7%A0%94%E7%A9%B6/%E5%AE%B9%E5%99%A8%E5%AE%89%E5%85%A8/%E5%AE%B9%E5%99%A8%E9%9B%86%E7%BE%A4%E5%AE%89%E5%85%A8/k8s/%E6%BA%90%E7%A0%81%E5%AE%A1%E8%AE%A1/%E5%A6%82%E4%BD%95%E5%BC%80%E5%8F%91%E5%B9%B6%E7%BC%96%E8%AF%91%E4%BB%A3%E7%A0%81/kubelet-%E8%BF%9C%E7%A8%8B%E8%B0%83%E8%AF%95.html

          參考資料

          [1]

          k8s makefile 源碼分析: https://ssst0n3.github.io/post/網(wǎng)絡(luò)安全/安全研究/容器安全/容器集群安全/k8s/源碼審計(jì)/如何開發(fā)并編譯代碼/k8s-makefile-源碼分析.html

          [2]

          delve: https://github.com/go-delve/delve

          [3]

          盡管我們也可以使用gdb調(diào)試go語言程序: https://go.dev/doc/gdb

          瀏覽 143
          點(diǎn)贊
          評(píng)論
          收藏
          分享

          手機(jī)掃一掃分享

          分享
          舉報(bào)
          評(píng)論
          圖片
          表情
          推薦
          點(diǎn)贊
          評(píng)論
          收藏
          分享

          手機(jī)掃一掃分享

          分享
          舉報(bào)
          <kbd id="afajh"><form id="afajh"></form></kbd>
          <strong id="afajh"><dl id="afajh"></dl></strong>
            <del id="afajh"><form id="afajh"></form></del>
                1. <th id="afajh"><progress id="afajh"></progress></th>
                  <b id="afajh"><abbr id="afajh"></abbr></b>
                  <th id="afajh"><progress id="afajh"></progress></th>
                  www.婷婷六月天 | 欧美a网站 | 五月天av在线 | 免费在线一级片 | 欧美pmⅴ|