<?xml version="1.0" encoding="UTF-8"?><rss version="2.0"
	xmlns:content="http://purl.org/rss/1.0/modules/content/"
	xmlns:wfw="http://wellformedweb.org/CommentAPI/"
	xmlns:dc="http://purl.org/dc/elements/1.1/"
	xmlns:atom="http://www.w3.org/2005/Atom"
	xmlns:sy="http://purl.org/rss/1.0/modules/syndication/"
	xmlns:slash="http://purl.org/rss/1.0/modules/slash/"
	>

<channel>
	<title>Cloud &#8211; richliu&#039;s blog</title>
	<atom:link href="https://blog.richliu.com/category/computer/cloud/feed/" rel="self" type="application/rss+xml" />
	<link>https://blog.richliu.com</link>
	<description>Linux, 工作, 生活, 家人</description>
	<lastBuildDate>Sun, 17 Sep 2023 17:24:54 +0000</lastBuildDate>
	<language>zh-TW</language>
	<sy:updatePeriod>
	hourly	</sy:updatePeriod>
	<sy:updateFrequency>
	1	</sy:updateFrequency>
	<generator>https://wordpress.org/?v=6.6.2</generator>
	<item>
		<title>Install phpIPAM on Kubernetes</title>
		<link>https://blog.richliu.com/2023/09/17/5342/install-phpipam-on-kubernetes/</link>
					<comments>https://blog.richliu.com/2023/09/17/5342/install-phpipam-on-kubernetes/#respond</comments>
		
		<dc:creator><![CDATA[richliu]]></dc:creator>
		<pubDate>Sun, 17 Sep 2023 15:38:20 +0000</pubDate>
				<category><![CDATA[Cloud]]></category>
		<category><![CDATA[kubernetes]]></category>
		<guid isPermaLink="false">https://blog.richliu.com/?p=5342</guid>

					<description><![CDATA[<p>This article is talking about how to install phpIPAM on [&#8230;]</p>
<p>The post <a rel="nofollow" href="https://blog.richliu.com/2023/09/17/5342/install-phpipam-on-kubernetes/">Install phpIPAM on Kubernetes</a> appeared first on <a rel="nofollow" href="https://blog.richliu.com">richliu&#039;s blog</a>.</p>
]]></description>
										<content:encoded><![CDATA[
<p>This article is talking about how to install <a href="https://phpipam.net/" target="_blank" rel="noreferrer noopener">phpIPAM </a>on Kubernetes, some thought might be used on other package . </p>



<p>It used the helm to install the <a href="https://artifacthub.io/packages/helm/phpipam/phpipam" target="_blank" rel="noreferrer noopener">phpipam</a>(helm version) on K8s.</p>



<span id="more-5342"></span>



<h2 class="wp-block-heading">Install phpipam command</h2>



<pre class="wp-block-preformatted">kubectl create namespace phpipam
kubectl create secret generic mysql-password --from-literal='password=&lt;mysql password&gt;' -n phpipam

helm repo add phpipam https://nullconfig.github.io/phpipam/stable
helm repo update
helm install --namespace phpipam --create-namespace phpipam phpipam/phpipam</pre>



<h2 class="wp-block-heading">Setup Storage</h2>



<p>if you have not setup the phpipam storge or default storage, it will show warning message on describe pods like this </p>



<pre class="wp-block-preformatted">$ kubectl describe pods phpipam-5f5f456d75-69hk7 -n phpipam

Events:
  Type     Reason            Age                 From               Message
  ----     ------            ----                ----               -------
  Warning  FailedScheduling  17s (x4 over 3m8s)  default-scheduler  0/3 nodes are available: pod has unbound immediate PersistentVolume
Claims. preemption: 0/3 nodes are available: 3 Preemption is not helpful for scheduling..
</pre>



<p>That&#8217;s means there is no <a href="https://kubernetes.io/docs/concepts/storage/persistent-volumes/" target="_blank" rel="noreferrer noopener">PersistentVolume </a>(pv) and PersistentVolume Claims (pvc) on your system, it needs to create one.</p>



<p>Here is pv.yaml contain. </p>



<pre class="wp-block-preformatted">apiVersion: v1
kind: PersistentVolume
metadata:
  name: phpipam
  namespace: phpipam
spec:
  capacity:
    storage: 100Gi
  accessModes:
    - ReadWriteOnce
  persistentVolumeReclaimPolicy: Retain
  storageClassName: local-storage
  local:
    path: /data
  nodeAffinity:
    required:
      nodeSelectorTerms:
      - matchExpressions:
        - key: kubernetes.io/hostname
          operator: In
          values:
          - k8s-node1
</pre>



<p>k8s-node1 is your storage node, function <a href="https://kubernetes.io/docs/concepts/storage/volumes/#local" target="_blank" rel="noreferrer noopener">local</a>: only can save storage on one node, if you setup it on master node, it will see this error message </p>



<pre class="wp-block-preformatted">Events:
  Type     Reason            Age    From               Message
  ----     ------            ----   ----               -------
  Warning  FailedScheduling  2m11s  default-scheduler  0/3 nodes are available: persistentvolumeclaim "phpipam" not found. preemption:
0/3 nodes are available: 3 Preemption is not helpful for scheduling..
  Warning  FailedScheduling  34s    default-scheduler  0/3 nodes are available: pod has unbound immediate PersistentVolumeClaims. preem
ption: 0/3 nodes are available: 3 Preemption is not helpful for scheduling..
  Warning  FailedScheduling  31s    default-scheduler  0/3 nodes are available: 1 node(s) had untolerated taint {node-role.kubernetes.i
o/control-plane: }. preemption: 0/3 nodes are available: 1 Preemption is not helpful for scheduling, 2 No preemption victims found for
incoming pod..
</pre>



<p>It needs to prepare pvc.yaml</p>



<pre class="wp-block-preformatted">apiVersion: v1
kind: PersistentVolumeClaim
metadata:
  name: phpipam
  namespace: phpipam
spec:
  accessModes:
    - ReadWriteOnce
  storageClassName: local-storage
  resources:
    requests:
      storage: 100Gi
</pre>



<p>Then, it can run apply them </p>



<pre class="wp-block-preformatted">kubectl apply -f pv.yaml 
kubectl apply -f pvc.yaml 
kubectl get pv -A
kubectl get pvc -A</pre>



<h2 class="wp-block-heading">Change the phpIPAM type from ClusterIP to LoadBalancer </h2>



<p>After finish setup the system, it needs to change the phpipam-web&#8217;s CludsterIIP to LoadBalancer to get external IP</p>



<pre class="wp-block-preformatted">$ kubectl get svc -A
phpipam          phpipam-db                  ClusterIP      10.101.2.59      &lt;none&gt;            3306/TCP                     3h22m
phpipam          phpipam-web                 ClusterIP      10.108.147.73    &lt;none&gt;            80/TCP                       3h22m
$ kubectl patch svc phpipam-web -n phpipam -p '{"spec": {"ports": [{"port": 443,"targetPort": 443,"name": "https"},
{"port": 80,"targetPort": 80,"name": "http"}],"type": "LoadBalancer"}}'
$ kubectl get svc -A
phpipam          phpipam-db                  ClusterIP      10.101.2.59      &lt;none&gt;            3306/TCP                     4h18m
phpipam          phpipam-web                 LoadBalancer   10.108.147.73    192.168.110.202   443:32226/TCP,80:30911/TCP   4h18m
</pre>



<p>Now, it can use browser to access the phpIPAM web via IP 192.168.110.202</p>



<figure class="wp-block-image size-full"><img fetchpriority="high" decoding="async" width="1141" height="604" src="https://blog.richliu.com/wp-content/uploads/2023/09/image-3.png" alt="" class="wp-image-5343" srcset="https://blog.richliu.com/wp-content/uploads/2023/09/image-3.png 1141w, https://blog.richliu.com/wp-content/uploads/2023/09/image-3-600x318.png 600w, https://blog.richliu.com/wp-content/uploads/2023/09/image-3-768x407.png 768w" sizes="(max-width: 1141px) 100vw, 1141px" /></figure>



<p>ref.<br /><a href="https://stackoverflow.com/questions/51559159/kubectl-how-to-edit-service-spec-type-to-loadbalancer-via-command-line" target="_blank" rel="noreferrer noopener">kubectl &#8211; How to edit service spec type to LoadBalancer via command line?</a></p>
<p>The post <a rel="nofollow" href="https://blog.richliu.com/2023/09/17/5342/install-phpipam-on-kubernetes/">Install phpIPAM on Kubernetes</a> appeared first on <a rel="nofollow" href="https://blog.richliu.com">richliu&#039;s blog</a>.</p>
]]></content:encoded>
					
					<wfw:commentRss>https://blog.richliu.com/2023/09/17/5342/install-phpipam-on-kubernetes/feed/</wfw:commentRss>
			<slash:comments>0</slash:comments>
		
		
			</item>
		<item>
		<title>ARM64 Kubernetes Qemu Metallb Linkerd Numa</title>
		<link>https://blog.richliu.com/2023/09/17/5329/arm64-kubernetes-qemu-metallb-linkerd-numa/</link>
					<comments>https://blog.richliu.com/2023/09/17/5329/arm64-kubernetes-qemu-metallb-linkerd-numa/#respond</comments>
		
		<dc:creator><![CDATA[richliu]]></dc:creator>
		<pubDate>Sat, 16 Sep 2023 16:46:48 +0000</pubDate>
				<category><![CDATA[ARM]]></category>
		<category><![CDATA[Cloud]]></category>
		<category><![CDATA[aarch64]]></category>
		<category><![CDATA[arm64]]></category>
		<category><![CDATA[kubernetes]]></category>
		<category><![CDATA[libvirt]]></category>
		<category><![CDATA[linkerd]]></category>
		<category><![CDATA[metallb]]></category>
		<category><![CDATA[numa]]></category>
		<category><![CDATA[qemu]]></category>
		<guid isPermaLink="false">https://blog.richliu.com/?p=5329</guid>

					<description><![CDATA[<p>Sometime I feelt hat k8s make me frustrated, Latest tim [&#8230;]</p>
<p>The post <a rel="nofollow" href="https://blog.richliu.com/2023/09/17/5329/arm64-kubernetes-qemu-metallb-linkerd-numa/">ARM64 Kubernetes Qemu Metallb Linkerd Numa</a> appeared first on <a rel="nofollow" href="https://blog.richliu.com">richliu&#039;s blog</a>.</p>
]]></description>
										<content:encoded><![CDATA[
<p>Sometime I feelt hat k8s make me frustrated,  Latest time I wrote this document is 4 years ago, that&#8217;s old version, but when I want to use k8s as container manager again, seems that something different and network won&#8217;t work, original document cannot work anymore, it needs to have new document to record that. </p>



<p>My hardware also different, if you don&#8217;t have such powerful machine, it can skip numa part, that&#8217;s only for high end ARM64 machine. <br />The hardware is <a href="https://amperecomputing.com/systems/altra/2u-mt-collins-2s-sas-3.5" target="_blank" rel="noreferrer noopener">Ampere Mt. Collins</a> which has 2*Ampere Altra 80 Cores CPU and 8*32G Memory, my experiment is run different VM on different CPU, to seperate them and lock it on different numa node. </p>



<span id="more-5329"></span>



<p>There are two CPUs, so, it can create 3 nodes, so, I have plan to allocate resource like that. <br />1. k8s master on socket 0: 10 CPUs, 16G memory <br />2. k8s node1 on socket 0 : 70 CPUs, 100G memory <br />3. k8s node2 on socket 1:  80 CPUs, 120G memory </p>



<p>Kubernetes version v1.28.2<br />Ubuntu 22.04</p>



<p><strong><mark style="background-color:rgba(0, 0, 0, 0)" class="has-inline-color has-luminous-vivid-orange-color">Notice: Before reading this document, this document is personal experiment, not Ampere official document, take your own risk. </mark></strong></p>



<h2 class="wp-block-heading">Prepare VM from libvirt </h2>



<p>The server has remote control system which problem sufficent resolution to use GUI on server, so, I install ubuntu 22.04 on host system, than use virt-manager to create k8s master node, for qemu image, I create the disk image alone, seems create image when run install will allocate all disk space, seems that&#8217;s a virt-manager bug. <br />And the host network is configured to be a bridge interface, in my case, that&#8217;s br0. </p>



<p>So, when uses virt-manager to create VM, it can bridge network interface to br0. </p>



<figure class="wp-block-image size-full"><img decoding="async" width="2125" height="1179" src="https://blog.richliu.com/wp-content/uploads/2023/09/image-1.png" alt="" class="wp-image-5330" srcset="https://blog.richliu.com/wp-content/uploads/2023/09/image-1.png 2125w, https://blog.richliu.com/wp-content/uploads/2023/09/image-1-600x333.png 600w, https://blog.richliu.com/wp-content/uploads/2023/09/image-1-768x426.png 768w, https://blog.richliu.com/wp-content/uploads/2023/09/image-1-1536x852.png 1536w, https://blog.richliu.com/wp-content/uploads/2023/09/image-1-2048x1136.png 2048w" sizes="(max-width: 2125px) 100vw, 2125px" /><figcaption class="wp-element-caption">After installed first VM, it can copy the master image to another VMs images and named it as k8s-node1 and k8s-node2. <br />need to modify the /etc/hostname, /etc/hosts and /etc/netplan/00-installer-config.yaml in the guest. <br />Remeber to change the CPU number and memory size on virt-manager GUI, different VM needs to use different VM image. it can keep other options by default. </figcaption></figure>



<h2 class="wp-block-heading">Configure the VM with Numa </h2>



<p>It can use numastat to check currnet numa status, this system has two numa nodes. it can use numastat and numactl to get more numa information.</p>



<pre class="wp-block-preformatted"># numastat -n

Per-node numastat info (in MBs):
                          Node 0          Node 1           Total
                 --------------- --------------- ---------------
Numa_Hit               591239.17       791075.41      1382314.58
Numa_Miss                   0.00            0.00            0.00
Numa_Foreign                0.00            0.00            0.00
Interleave_Hit              8.63            7.13           15.77
Local_Node             519434.17       777974.99      1297409.16
Other_Node              71805.00        13100.42        84905.42

# numactl --hardware
available: 2 nodes (0-1)
node 0 cpus: 0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79
node 0 size: 128377 MB
node 0 free: 80224 MB
node 1 cpus: 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159
node 1 size: 126426 MB
node 1 free: 93888 MB
node distances:
node   0   1
  0:  10  20
  1:  20  10</pre>



<p>virt-manager doesn&#8217;t have advance command to assign CPU, probably modify xml can get that purpose, but it more converince to use the &#8220;virsh&#8221; cli command to adjust VM parameters. &#8220;virsh list&#8221; show current VMs, &#8220;virsh vcpupin list current VM CPU scheduling&#8221;, &#8220;virsh vcpupin <em>domain-id vcpu cpulist</em>&#8221; to modify the VCPU run on which one CPU. </p>



<p>For memory, it needs to use &#8220;virsh numatune&#8221; to lock the memory on different node. <br />&#8220;virsh numatune domain [&#8211;mode mode] [&#8211;nodeset nodeset] [[&#8211;config] [&#8211;live] | [&#8211;current]]&#8221;, &#8211;current can update current running VM machine. </p>



<pre class="wp-block-preformatted">$ virsh list
 Id   Name          State
-----------------------------
 9    k8s-master   running
 10   k8s-node1     running

$ virsh vcpupin k8s-master
 VCPU   CPU Affinity
----------------------
 0      0-159
 1      0-159
 2      0-159
 3      0-159
 4      0-159
 5      0-159
 6      0-159
 7      0-159
 8      0-159
 9      0-159

# this command can lock 9 k8s-master's VCPU 0 on physical CPU 0. 
$ virsh vcpupin 9 0 0 

# Show current VM's numatune, for example, following is unset status. 
$ virsh numatune 9
numa_mode      : strict
numa_nodeset   :

$ virsh numatune 9 --nodeset 0

# the numa_nodeset was set to 0
$ virsh numatune 9
numa_mode      : strict
numa_nodeset   : 0

</pre>



<p>The problem is, seems this script need to run everytime, alternativate solution is to modify XML, but Mt. collis has 160 cores, I won&#8217;t to modify the XML file. script is more converience on this situation, following is my sample script to adjust k8s-master, k8s-node1, and k8s-node2&#8217;s parameter, it can easy to modify it if you install other system or AltraMax CPU. </p>



<pre class="wp-block-preformatted">#!/bin/bash

configure_vm(){
        local VM_NAME="$1"
        local VM_VCPU="$2"
        local VM_CPU="$3"
        local VM_NUMA="$4"
        local VM_TYPE="$5" # VM_TYPE for MASTER or NODE0, NODE1 .. self define name

        id=$(virsh list | grep $VM_NAME | awk '{print $1}')
        state=$(virsh list | grep $VM_NAME | awk '{print $3}')

        if [ "$state" != "running" ]; then
          echo "$VM_TYPE is not running"
          exit 1
        else
          echo "configure $VM_TYPE"
        fi
        numa_nodeset=$(virsh numatune $id | grep numa_nodeset | awk '{print $3}')

        start_cpu=$(echo $VM_VCPU | cut -d'-' -f1)
        end_cpu=$(echo $VM_VCPU | cut -d'-' -f2)
        for ((vcpu = start_cpu; vcpu &lt;= end_cpu; vcpu++)); do
          # echo "$id $vcpu $VM_CPU"
          virsh vcpupin $id $vcpu $VM_CPU > /dev/null
        done
        if [ -n "$numa_nodeset" ]; then
          echo "$VM_TYPE numa_nodeset is $numa_nodeset"
        else
          # echo "$id $VM_NUMA"
          virsh numatune $id --nodeset $VM_NUMA
        fi
}

configure_vm "k8s-master" "0-9" "0-9" "0" "Master"
configure_vm "k8s-node1" "0-69" "10-79" "0" "Node0"
configure_vm "k8s-node2" "0-79" "80-159" "1" "Node1"


====

# After run the script, it can run numastat &lt;pid> to see the qemu runs numa status. ex:
$ sudo numastat 206601

Per-node process memory usage (in MBs) for PID 206601 (qemu-system-aar)
                           Node 0          Node 1           Total
                  --------------- --------------- ---------------
Huge                         0.00            0.00            0.00
Heap                        11.51            0.00           11.51
Stack                        0.04            0.00            0.04
Private                   5984.93            0.00         5984.94
----------------  --------------- --------------- ---------------
Total                     5996.48            0.00         5996.48

</pre>



<p>In here, on socket 0 , 0-9 and 0-69 is vcpu, so, all start from 0. After run this script, it can use &#8220;virsh vcpupin&#8221; and &#8220;virsh numatune&#8221; to get current setting. Maybe cpuset parameter in XML can more easy to get this function, but I have not try it. </p>



<p></p>



<h2 class="wp-block-heading">Install K8s </h2>



<p>Here is my script, just reference some later blog and my previous configurtion script, so, it can copy and paste to system and run it directly. </p>



<p>Install basic system and k8s</p>



<pre class="wp-block-preformatted"># setup timezone
sudo apt install ntpdate -y
sudo ntpdate watch.stdtime.gov.tw
sudo timedatectl set-timezone Asia/Taipei

# install and enable docker

sudo curl -fsSL https://download.docker.com/linux/ubuntu/gpg | sudo gpg --dearmour -o /etc/apt/trusted.gpg.d/docker.gpg
sudo add-apt-repository "deb [arch=$(dpkg --print-architecture)] https://download.docker.com/linux/ubuntu $(lsb_release -cs) stable"

sudo apt update
sudo apt install -y containerd.io

containerd config default | sudo tee /etc/containerd/config.toml >/dev/null 2>&amp;1
sudo sed -i 's/SystemdCgroup \= false/SystemdCgroup \= true/g' /etc/containerd/config.toml

sudo systemctl restart containerd
sudo systemctl enable containerd

echo "----------------"
echo "   swapoff"
echo "----------------"
sudo swapoff -a
sudo sed -i '/swap/ s/^\(.*\)$/#\1/g' /etc/fstab

# Install k8s
sudo apt -y install apt-transport-https curl
curl -s https://packages.cloud.google.com/apt/doc/apt-key.gpg | sudo apt-key add
sudo apt-add-repository "deb http://apt.kubernetes.io/ kubernetes-xenial main"
sudo apt update

sudo apt-get -y install kubelet
sudo apt-get -y install kubeadm
sudo apt-get -y install kubectl
sudo apt-mark hold kubelet kubeadm kubectl

# Update kernel parametes
cat &lt;&lt;EOF | sudo tee /etc/sysctl.d/99-kubernetes-cri.conf
net.bridge.bridge-nf-call-iptables  = 1
net.ipv4.ip_forward                 = 1
net.bridge.bridge-nf-call-ip6tables = 1
EOF

# update sysctl
sudo sysctl --system

sudo tee /etc/modules-load.d/containerd.conf &lt;&lt;EOF
overlay
br_netfilter
EOF
sudo modprobe overlay
sudo modprobe br_netfilter

echo "if this is work node, it can run kubeadm join now"

echo "alias k=kubectl" >> .bashrc</pre>



<h3 class="wp-block-heading">Setup Master Node</h3>



<p>Run this script on master node. </p>



<pre class="wp-block-preformatted">sudo kubeadm init --pod-network-cidr=10.244.0.0/16
mkdir -p $HOME/.kube
sudo cp -i /etc/kubernetes/admin.conf $HOME/.kube/config
sudo chown $(id -u):$(id -g) $HOME/.kube/config

# echo "enable master to run pods"
# kubectl taint nodes --all node-role.kubernetes.io/master-
</pre>



<p>It will shows some message below, then run it on k8s-node1 and k8s-node2</p>



<p>kubeadm join 192.168.110.230:6443 &#8211;token e14f7k.35c3jpny81ry70re \</p>



<p>        &#8211;discovery-token-ca-cert-hash sha256:6636a7e4ec3542f19152f308f0789c52287b743b60efa3c13e7c23ce1147c581</p>



<p>If forgot command above, it can create another token to let other k8s node join, ex:</p>



<pre class="wp-block-preformatted">kubeadm token create --print-join-command</pre>



<h3 class="wp-block-heading">Flannel : Network fabric for container</h3>



<p>K8s need a network fabric to provide internal network topology, there are many choices, but we will install matellb later, some other network like calico might have potential issue, so, we choice flannel as network fabric.</p>



<pre class="wp-block-preformatted">kubectl apply -f https://github.com/flannel-io/flannel/releases/latest/download/kube-flannel.yml</pre>



<p>After run this command, the k8s node status will change to Ready, if not install network fabric, the node status will be NotReady. </p>



<pre class="wp-block-preformatted">$ kubectl get nodes
NAME         STATUS   ROLES           AGE   VERSION
k8s-master   Ready    control-plane   26h   v1.28.2
k8s-node1    Ready    &lt;none>          26h   v1.28.2
k8s-node2    Ready    &lt;none>          26h   v1.28.2</pre>



<h3 class="wp-block-heading">Helm: Kubbernetes Applications Manager</h3>



<p>Install helm to further install metallb purpose, on previous article, helm2 needs another application to connect to k8s, but helm3 doesn&#8217;t need it, more easy to use on k8s. </p>



<pre class="wp-block-preformatted">curl -fsSL https://raw.githubusercontent.com/helm/helm/main/scripts/get-helm-3 -o /tmp/get_helm.sh
chmod 700 /tmp/get_helm.sh
sudo /tmp/get_helm.sh</pre>



<h3 class="wp-block-heading">Metallb: Bere metal load-balancer for K8s</h3>



<p>Install k8s on private side, it needs load-balancer to provide external IP to communication with internet or intranet. If you install Metallb, the &#8220;kubectl get svc&#8221;, the EXTERNAL-IP shows &#8220;Pending&#8221;, and k8s doesn&#8217;t response the arp on host, probably it doesn&#8217;t configure kube-proxy, it you have experience on previous metallb installtion, it might miss this part. </p>



<pre class="wp-block-preformatted">PATH=$PATH:/usr/local/bin/

helm repo add metallb https://metallb.github.io/metallb
helm --namespace metallb-system install --create-namespace metallb metallb/metallb -f metallb-values.yaml

# https://metallb.universe.tf/installation/
# see what changes would be made, returns nonzero returncode if different
kubectl get configmap kube-proxy -n kube-system -o yaml | \
        sed -e "s/strictARP: false/strictARP: true/" | \
        kubectl diff -f - -n kube-system

# actually apply the changes, returns nonzero returncode on errors only
kubectl get configmap kube-proxy -n kube-system -o yaml | \
        sed -e "s/strictARP: false/strictARP: true/" | \
        kubectl apply -f - -n kube-system
</pre>



<p>metallb-values.yaml is also different like previous setting, it needs to configure L2Advertisement on metallb, without it, your metallb won&#8217;t work. Follwing is metallb-values.yaml  file. </p>



<pre class="wp-block-preformatted">apiVersion: metallb.io/v1beta1
kind: IPAddressPool
metadata:
  name: primary-pool
  namespace: metallb-system
spec:
  addresses:
  - 192.168.110.200-192.168.110.219

---
apiVersion: metallb.io/v1beta1
kind: L2Advertisement
metadata:
  name: l2adv
  namespace: metallb-system
spec:
  ipAddressPools:
  - primary-pool
</pre>



<h3 class="wp-block-heading">Traefik: TBD</h3>



<h3 class="wp-block-heading">Linkerd</h3>



<p>Just show the install script here</p>



<pre class="wp-block-preformatted">curl --proto '=https' --tlsv1.2 -sSfL https://run.linkerd.io/install | sh

echo "export PATH=$PATH:/home/$USER/.linkerd2/bin" >> ~/.bashrc

linkerd install --crds | kubectl apply -f -
linkerd install | kubectl apply -f -
linkerd viz install | kubectl apply -f -</pre>



<h3 class="wp-block-heading">Other</h3>



<p>it can insert isolinux to host linux kernel parameter to isolate the Linux scheduling to k8s nodes. (TBD)</p>



<pre class="wp-block-preformatted">isolcpus=10-159 nohz=on nohz_full=10-159</pre>



<h2 class="wp-block-heading">Test with Nginx </h2>



<p>It can deploy nginx to test this system </p>



<pre class="wp-block-preformatted">kubectl create deploy nginx --image=nginx
kubectl expose deploy nginx --port=80 --target-port=80 --type=LoadBalancer
kubectl get svc nginx
NAME    TYPE           CLUSTER-IP      EXTERNAL-IP       PORT(S)        AGE
nginx   LoadBalancer   10.99.211.255   192.168.110.200   80:31011/TCP   25h</pre>



<p>Now, it can try to access http://192.168.110.200. <br />if want to Delete nginx deploy, run following command. </p>



<pre class="wp-block-preformatted">kubectl delete deploy nginx
kubectl delete svc nginx</pre>



<h2 class="wp-block-heading">Test Numa</h2>



<p>It can run emojivoto to test the system only runs on socket1, use it because it can general a lot of traffic between pods. </p>



<pre class="wp-block-preformatted">curl --proto '=https' --tlsv1.2 -sSfL https://run.linkerd.io/emojivoto.yml \
  | kubectl apply -f -</pre>



<p>Now it can use htop to show all CPUs, and we can see most traffic on CPU 1~10 and 81~160. There are a little CPU usage on CPU 78 and 80, but it should be Linux regular scheduling(I have not add isocpu to host CPU this time)</p>



<figure class="wp-block-image size-full"><img decoding="async" width="1982" height="857" src="https://blog.richliu.com/wp-content/uploads/2023/09/image-2.png" alt="" class="wp-image-5338" srcset="https://blog.richliu.com/wp-content/uploads/2023/09/image-2.png 1982w, https://blog.richliu.com/wp-content/uploads/2023/09/image-2-600x259.png 600w, https://blog.richliu.com/wp-content/uploads/2023/09/image-2-768x332.png 768w, https://blog.richliu.com/wp-content/uploads/2023/09/image-2-1536x664.png 1536w" sizes="(max-width: 1982px) 100vw, 1982px" /><figcaption class="wp-element-caption">ref.<br /><a href="https://blog.richliu.com/2019/11/01/4197/arm64-kubernetes-nginx-traefik-ingress-load-balance/" target="_blank" rel="noreferrer noopener">ARM64 Kubernetes Nginx Traefik Ingress Load Balance</a><br /><a href="https://blog.richliu.com/2019/09/25/4160/install-kubernetes-on-arm64-ubuntu-18-04/" target="_blank" rel="noreferrer noopener">Install Kubernetes on ARM64 Ubuntu 18.04 (with QEMU)</a><br /><a href="https://blog.richliu.com/2020/01/14/4256/kubernetes-install-nginx-ingress-on-arm64/" target="_blank" rel="noreferrer noopener">Kubernetes install nginx-ingress on ARM64</a><br /><a href="https://metallb.universe.tf/troubleshooting/" target="_blank" rel="noreferrer noopener">TROUBLESHOOTING METALLB</a><br /><a href="https://github.com/metallb/metallb/issues/1591" target="_blank" rel="noreferrer noopener">Reassignment Duplicate IP after deleting IP pool #1591</a><br /><a href="https://access.redhat.com/documentation/zh-tw/red_hat_enterprise_linux/7/html/virtualization_tuning_and_optimization_guide/sect-virtualization_tuning_optimization_guide-numa-numa_and_libvirt" target="_blank" rel="noreferrer noopener">9.3. libvirt NUMA Tuning</a><br /></figcaption></figure>
<p>The post <a rel="nofollow" href="https://blog.richliu.com/2023/09/17/5329/arm64-kubernetes-qemu-metallb-linkerd-numa/">ARM64 Kubernetes Qemu Metallb Linkerd Numa</a> appeared first on <a rel="nofollow" href="https://blog.richliu.com">richliu&#039;s blog</a>.</p>
]]></content:encoded>
					
					<wfw:commentRss>https://blog.richliu.com/2023/09/17/5329/arm64-kubernetes-qemu-metallb-linkerd-numa/feed/</wfw:commentRss>
			<slash:comments>0</slash:comments>
		
		
			</item>
		<item>
		<title>CentOS8 ARM64/AARCH64 Install Docker</title>
		<link>https://blog.richliu.com/2020/05/18/4273/centos8-arm64-aarch64-install-docker/</link>
					<comments>https://blog.richliu.com/2020/05/18/4273/centos8-arm64-aarch64-install-docker/#respond</comments>
		
		<dc:creator><![CDATA[richliu]]></dc:creator>
		<pubDate>Mon, 18 May 2020 15:11:17 +0000</pubDate>
				<category><![CDATA[Cloud]]></category>
		<category><![CDATA[Linux]]></category>
		<category><![CDATA[aarch64]]></category>
		<category><![CDATA[arm64]]></category>
		<category><![CDATA[centos8]]></category>
		<category><![CDATA[docker]]></category>
		<guid isPermaLink="false">https://blog.richliu.com/?p=4273</guid>

					<description><![CDATA[<p>It&#8217;s not complex to install docker on ARM64 platf [&#8230;]</p>
<p>The post <a rel="nofollow" href="https://blog.richliu.com/2020/05/18/4273/centos8-arm64-aarch64-install-docker/">CentOS8 ARM64/AARCH64 Install Docker</a> appeared first on <a rel="nofollow" href="https://blog.richliu.com">richliu&#039;s blog</a>.</p>
]]></description>
										<content:encoded><![CDATA[
<p>It&#8217;s not complex to install docker on ARM64 platform and make it work, but it needs a trick</p>



<span id="more-4273"></span>



<h2 class="wp-block-heading">Remove Packages </h2>



<p>$  sudo yum remove docker-ce docker-ce-cli containerd.io </p>



<h2 class="wp-block-heading">Install Containterd First</h2>



<p>This is most important step, without this, docker&#8217;s install script will fail. </p>



<p>$ sudo dnf install <a href="https://download.docker.com/linux/centos/7/aarch64/stable/Packages/containerd.io-1.2.6-3.3.el7.aarch64.rpm" target="_blank" rel="noopener">https://download.docker.com/linux/centos/7/aarch64/stable/Packages/containerd.io-1.2.6-3.3.el7.aarch64.rpm</a></p>



<h2 class="wp-block-heading">Docker Script</h2>



<p>Get docker script and run it <br />$ curl -fsSL https://get.docker.com -o get-docker.sh <br />$ sudo sh get-docker.sh <br />Add your current username to docker group if not run on root account. <br />$ sudo usermod -aG docker your-user </p>



<h2 class="wp-block-heading">Restart Docker And Enable Firewall </h2>



<p>$  sudo systemctl start docker <br />$  firewall-cmd &#8211;zone=public &#8211;add-masquerade &#8211;permanent <br />$  firewall-cmd &#8211;reload </p>



<p>ref. <br />[1]  https://linuxconfig.org/how-to-install-docker-in-rhel-8 <br />[2]  https://docs.docker.com/engine/install/centos/ <br />[3]  https://serverfault.com/questions/987686/no-network-connectivity-to-from-docker-ce-container-on-centos-8 </p>
<p>The post <a rel="nofollow" href="https://blog.richliu.com/2020/05/18/4273/centos8-arm64-aarch64-install-docker/">CentOS8 ARM64/AARCH64 Install Docker</a> appeared first on <a rel="nofollow" href="https://blog.richliu.com">richliu&#039;s blog</a>.</p>
]]></content:encoded>
					
					<wfw:commentRss>https://blog.richliu.com/2020/05/18/4273/centos8-arm64-aarch64-install-docker/feed/</wfw:commentRss>
			<slash:comments>0</slash:comments>
		
		
			</item>
		<item>
		<title>Kubernetes install nginx-ingress on ARM64</title>
		<link>https://blog.richliu.com/2020/01/14/4256/kubernetes-install-nginx-ingress-on-arm64/</link>
					<comments>https://blog.richliu.com/2020/01/14/4256/kubernetes-install-nginx-ingress-on-arm64/#respond</comments>
		
		<dc:creator><![CDATA[richliu]]></dc:creator>
		<pubDate>Tue, 14 Jan 2020 04:01:00 +0000</pubDate>
				<category><![CDATA[ARM]]></category>
		<category><![CDATA[Cloud]]></category>
		<category><![CDATA[arm64]]></category>
		<category><![CDATA[k8s]]></category>
		<category><![CDATA[kubernetes]]></category>
		<category><![CDATA[nginx-ingress]]></category>
		<guid isPermaLink="false">https://blog.richliu.com/?p=4256</guid>

					<description><![CDATA[<p>It&#8217;s easy. it needs to install helm first and jus [&#8230;]</p>
<p>The post <a rel="nofollow" href="https://blog.richliu.com/2020/01/14/4256/kubernetes-install-nginx-ingress-on-arm64/">Kubernetes install nginx-ingress on ARM64</a> appeared first on <a rel="nofollow" href="https://blog.richliu.com">richliu&#039;s blog</a>.</p>
]]></description>
										<content:encoded><![CDATA[
<p>It&#8217;s easy. it needs to install helm first and just run following command </p>



<pre class="wp-block-code"><code>helm install \
    --name nginx-ingress stable/nginx-ingress \
    --namespace ingress-nginx \
    --set rbac.create=true \
    --set controller.image.repository="quay.io/kubernetes-ingress-controller/nginx-ingress-controller-arm64" \
    --set defaultBackend.image.repository="k8s.gcr.io/defaultbackend-arm64"
</code></pre>



<p>ref. <br /> https://github.com/kubernetes/ingress-nginx/issues/4876 <br /> https://github.com/kubernetes/ingress-nginx/pull/3852 </p>
<p>The post <a rel="nofollow" href="https://blog.richliu.com/2020/01/14/4256/kubernetes-install-nginx-ingress-on-arm64/">Kubernetes install nginx-ingress on ARM64</a> appeared first on <a rel="nofollow" href="https://blog.richliu.com">richliu&#039;s blog</a>.</p>
]]></content:encoded>
					
					<wfw:commentRss>https://blog.richliu.com/2020/01/14/4256/kubernetes-install-nginx-ingress-on-arm64/feed/</wfw:commentRss>
			<slash:comments>0</slash:comments>
		
		
			</item>
		<item>
		<title>Linkerd2 for ARM64</title>
		<link>https://blog.richliu.com/2019/12/06/4247/linkerd2-for-arm64/</link>
					<comments>https://blog.richliu.com/2019/12/06/4247/linkerd2-for-arm64/#respond</comments>
		
		<dc:creator><![CDATA[richliu]]></dc:creator>
		<pubDate>Fri, 06 Dec 2019 11:28:54 +0000</pubDate>
				<category><![CDATA[ARM]]></category>
		<category><![CDATA[Cloud]]></category>
		<category><![CDATA[arm64]]></category>
		<category><![CDATA[emojivoto]]></category>
		<category><![CDATA[kubernetes]]></category>
		<category><![CDATA[linkerd]]></category>
		<category><![CDATA[linkerd2]]></category>
		<guid isPermaLink="false">https://blog.richliu.com/?p=4247</guid>

					<description><![CDATA[<p>There is no regular ARM64 support for Linkerd2 now. So, [&#8230;]</p>
<p>The post <a rel="nofollow" href="https://blog.richliu.com/2019/12/06/4247/linkerd2-for-arm64/">Linkerd2 for ARM64</a> appeared first on <a rel="nofollow" href="https://blog.richliu.com">richliu&#039;s blog</a>.</p>
]]></description>
										<content:encoded><![CDATA[
<p>There is no regular ARM64 support for <a rel="noreferrer noopener" aria-label="Linkerd2  (opens in a new tab)" href="https://github.com/linkerd/linkerd2" target="_blank">Linkerd2 </a>now. <br /><br />So, I built one for test. <br />All necessary packages will be downloaded from my private docker.io account. not from regular linkerd2 repository. <br /><br />Linkerd2 version is master version between v2.6.0 and next version<br />emojivoto version is v9 (master version)</p>



<span id="more-4247"></span>



<p>First, download Linkerd2 binary for ARM64 from my github website. <br />There are some binary files in release directory, please ignore them, just for compile source code only. </p>



<pre class="wp-block-code"><code>git clone https://github.com/richliu/linkerd2-arm64.git
cd linkerd2-arm64/</code></pre>



<p>Install Linkerd2 for ARM64</p>



<pre class="wp-block-code"><code>kubectl apply -f arm64.yml</code></pre>



<p>It can also install Linkerd2 demo app emojivoto, yes, it doesn&#8217;t support ARM64, so, I ported it for ARM64 platform. </p>



<pre class="wp-block-code"><code>kubectl apply -f emojivoto.yml</code></pre>



<p>Check whether it running on your system . </p>



<figure class="wp-block-image"><img loading="lazy" decoding="async" width="1024" height="376" src="https://blog.richliu.com/wp-content/uploads/2019/12/image-1024x376.png" alt="" class="wp-image-4248" srcset="https://blog.richliu.com/wp-content/uploads/2019/12/image-1024x376.png 1024w, https://blog.richliu.com/wp-content/uploads/2019/12/image-300x110.png 300w, https://blog.richliu.com/wp-content/uploads/2019/12/image-768x282.png 768w, https://blog.richliu.com/wp-content/uploads/2019/12/image.png 1478w" sizes="(max-width: 1024px) 100vw, 1024px" /></figure>



<p>Now, it can follow <a rel="noreferrer noopener" aria-label="linkerd Getting Started  (opens in a new tab)" href="https://linkerd.io/2/getting-started/" target="_blank">linkerd Getting Started </a>to test  linkerd2  on ARM64 platform. <br /><br />ref. <br /><a href="https://github.com/linkerd/linkerd2/issues/1165#" target="_blank" rel="noopener">Support for ARM based architectures?</a></p>
<p>The post <a rel="nofollow" href="https://blog.richliu.com/2019/12/06/4247/linkerd2-for-arm64/">Linkerd2 for ARM64</a> appeared first on <a rel="nofollow" href="https://blog.richliu.com">richliu&#039;s blog</a>.</p>
]]></content:encoded>
					
					<wfw:commentRss>https://blog.richliu.com/2019/12/06/4247/linkerd2-for-arm64/feed/</wfw:commentRss>
			<slash:comments>0</slash:comments>
		
		
			</item>
		<item>
		<title>ARM64 Kubernetes Nginx Traefik Ingress Load Balance</title>
		<link>https://blog.richliu.com/2019/11/01/4197/arm64-kubernetes-nginx-traefik-ingress-load-balance/</link>
					<comments>https://blog.richliu.com/2019/11/01/4197/arm64-kubernetes-nginx-traefik-ingress-load-balance/#respond</comments>
		
		<dc:creator><![CDATA[richliu]]></dc:creator>
		<pubDate>Fri, 01 Nov 2019 11:47:07 +0000</pubDate>
				<category><![CDATA[ARM]]></category>
		<category><![CDATA[Cloud]]></category>
		<category><![CDATA[arm64]]></category>
		<category><![CDATA[kubernetes]]></category>
		<category><![CDATA[metallb]]></category>
		<category><![CDATA[traefik]]></category>
		<guid isPermaLink="false">https://blog.richliu.com/?p=4197</guid>

					<description><![CDATA[<p>My original target purpose is very simple, build deploy [&#8230;]</p>
<p>The post <a rel="nofollow" href="https://blog.richliu.com/2019/11/01/4197/arm64-kubernetes-nginx-traefik-ingress-load-balance/">ARM64 Kubernetes Nginx Traefik Ingress Load Balance</a> appeared first on <a rel="nofollow" href="https://blog.richliu.com">richliu&#039;s blog</a>.</p>
]]></description>
										<content:encoded><![CDATA[
<p>My original target purpose is very simple, build deploy several webserver and assigned a external ip for internet to access it. <br /><br />Most kubernetes newbie install guide won&#8217;t mention how to do that. actually that&#8217;s very simple, for external ip, it needs a load balance controller like metallb for create a external ip address to access web server. and an Ingress contoller like Traefik for http/https route to right pods .</p>



<span id="more-4197"></span>



<figure class="wp-block-image"><img decoding="async" src="https://i1.wp.com/www.devtech101.com/wp-content/uploads/2019/02/metal-lb_part1.png?resize=648%2C314&amp;ssl=1" alt=""/><figcaption>ref:  <a href="https://www.devtech101.com/2019/02/23/using-metallb-and-traefik-load-balancing-for-your-bare-metal-kubernetes-cluster-part-1/" target="_blank" rel="noopener">Using MetalLB And Traefik for Load balancing on your Bare Metal Kubernetes Cluster – Part 1</a> </figcaption></figure>



<p>Above is a figure to describe relationship about metallb/traefik and kubernetes. <br /><br />Please reference previous article (<a href="https://blog.richliu.com/2019/09/25/4160/install-kubernetes-on-arm64-ubuntu-18-04">Install Kubernetes on ARM64 Ubuntu 18.04</a>)about how to setup environment. </p>



<h3 class="wp-block-heading">Install Helm</h3>



<p>First, install Helm, helm is a kubernetes packages manager. it can help to install traefik, for some package, like traefik, it&#8217;s not easy to install manually, I tried, but fail. Use helm to install is a good idea. <br /><br />Following instruction can download and install helm, or you can visit helm webpage for latest version <br /><br />Following is command to download and install helm.</p>



<pre class="wp-block-preformatted">wget https://get.helm.sh/helm-v2.15.1-linux-arm64.tar.gz
tar xvf helm-v2.15.1-linux-arm64.tar.gz
sudo mv linux-arm64/helm /usr/bin</pre>



<p>Default helm(tiller seems doesn&#8217;t support ARM64 archeticture, so, it needs to use third party binary code for tiller. In here we used <a href="https://github.com/jessestuart/tiller-multiarch" target="_blank" rel="noopener">tiller-multiarch</a>.  </p>



<pre class="wp-block-preformatted">helm init --tiller-image=jessestuart/tiller </pre>



<h4 class="wp-block-heading">Helm install error message </h4>



<p>When you run helm install command, if see error message like below, please try to follow this step to solve it. (ref: <a rel="noreferrer noopener" aria-label="TILLER AND ROLE-BASED ACCESS CONTROL (opens in a new tab)" href="https://helm.sh/docs/using_helm/#tiller-and-role-based-access-control" target="_blank">TILLER AND ROLE-BASED ACCESS CONTROL</a> and <a rel="noreferrer noopener" aria-label="forbidden: User &quot;system:serviceaccount:kube-system:default&quot; cannot get namespaces in the namespace &quot;default (opens in a new tab)" href="https://github.com/fnproject/fn-helm/issues/21" target="_blank">forbidden: User &#8220;system:serviceaccount:kube-system:default&#8221; cannot get namespaces in the namespace &#8220;default</a>)<br /><br />Create a rbac-config.yaml like following text<br />(ref. <a href="https://github.com/helm/helm/issues/3130" target="_blank" rel="noopener">User &#8220;system:serviceaccount:kube-system:default&#8221; cannot get namespaces in the namespace &#8220;default&#8221;</a> )</p>



<pre class="wp-block-code"><code>apiVersion: v1
kind: ServiceAccount
metadata:
  name: tiller
  namespace: default
---
apiVersion: rbac.authorization.k8s.io/v1beta1
kind: ClusterRoleBinding
metadata:
  name: tiller
roleRef:
  apiGroup: rbac.authorization.k8s.io
  kind: ClusterRole
  name: cluster-admin
subjects:
  - kind: ServiceAccount
    name: tiller
    namespace: default</code></pre>



<p>Run following command to create  and upgrade helm initial </p>



<pre class="wp-block-preformatted">kubectl create -f rbac-config.yaml
helm init --service-account tiller --history-max 200 --tiller-image=jessestuart/tiller --upgrade</pre>



<p>or run those commands directly. </p>



<pre class="wp-block-preformatted">kubectl create serviceaccount --namespace kube-system tiller<br />kubectl create clusterrolebinding tiller-cluster-rule --clusterrole=cluster-admin --serviceaccount=kube-system:tiller<br />kubectl patch deploy --namespace kube-system tiller-deploy -p '{"spec":{"template":{"spec":{"serviceAccount":"tiller"}}}}'<br />helm init --upgrade --service-account tiller </pre>



<h3 class="wp-block-heading">Install metallb </h3>



<h4 class="wp-block-heading">Automatically Install</h4>



<p>It can use helm to install automatically, first create a metallb-config.yaml, contain like below.</p>



<pre class="wp-block-preformatted">configInline:
   address-pools:
   - name: default 
     protocol: layer2
     addresses:
         - 192.168.110.80-192.168.110.100 </pre>



<p>Save it, and run follow command to apply it. </p>



<pre class="wp-block-preformatted">helm install --name=metallb --namespace=metallb-system -f  metallb-config.yaml stable/metallb </pre>



<figure class="wp-block-image"><img loading="lazy" decoding="async" width="1024" height="641" src="https://blog.richliu.com/wp-content/uploads/2019/10/image-1-1024x641.png" alt="" class="wp-image-4201" srcset="https://blog.richliu.com/wp-content/uploads/2019/10/image-1-1024x641.png 1024w, https://blog.richliu.com/wp-content/uploads/2019/10/image-1-300x188.png 300w, https://blog.richliu.com/wp-content/uploads/2019/10/image-1-768x481.png 768w, https://blog.richliu.com/wp-content/uploads/2019/10/image-1.png 1631w" sizes="(max-width: 1024px) 100vw, 1024px" /></figure>



<h4 class="wp-block-heading">Manually Install</h4>



<p>It also can install metallb manually, run following command to install it.<br />It will install v0.8.1, it can visit <a rel="noreferrer noopener" aria-label="metallb website (opens in a new tab)" href="https://metallb.universe.tf/installation/" target="_blank">metallb website</a> to check latest version.</p>



<pre class="wp-block-preformatted">kubectl apply -f <a href="https://raw.githubusercontent.com/google/metallb/v0.8.1/manifests/metallb.yaml" target="_blank" rel="noopener">https://raw.githubusercontent.com/google/metallb/v0.8.1/manifests/metallb.yaml</a> </pre>



<p>Add a new file name metallb.yaml and put follow text</p>



<pre class="wp-block-preformatted">apiVersion: v1
kind: ConfigMap
metadata:
   namespace: metallb-system
   name: config
data:
   config: |
     address-pools:
     - name: my-ip-space
       protocol: layer2
       addresses:
       - 192.168.110.70/28</pre>



<p>Apply it</p>



<pre class="wp-block-preformatted">kubectl apply -f  metallb.yaml </pre>



<h3 class="wp-block-heading">Install Traefik</h3>



<p>Traefik is an open-source Edge Router that makes publishing your services a fun and easy experience.<br /><br />Following is command to initial helm and used helm to initial traefik. </p>



<pre class="wp-block-preformatted">helm install stable/traefik --name traefik --set dashboard.enabled=true,serviceType=NodePort,dashboard.domain=dashboard-traefik.techarea.org,rbac.enabled=true  --namespace kube-system</pre>



<figure class="wp-block-image"><img loading="lazy" decoding="async" width="1024" height="890" src="https://blog.richliu.com/wp-content/uploads/2019/10/image-2-1024x890.png" alt="" class="wp-image-4202" srcset="https://blog.richliu.com/wp-content/uploads/2019/10/image-2-1024x890.png 1024w, https://blog.richliu.com/wp-content/uploads/2019/10/image-2-300x261.png 300w, https://blog.richliu.com/wp-content/uploads/2019/10/image-2-768x668.png 768w, https://blog.richliu.com/wp-content/uploads/2019/10/image-2.png 1272w" sizes="(max-width: 1024px) 100vw, 1024px" /></figure>



<h4 class="wp-block-heading">Traefik Dashboard</h4>



<p>When used helm to install traefik, it also install traefik dashboard on dashboard-traefik.techarea.org. <br /><br />Used following command to get traefik web service ip</p>



<pre class="wp-block-preformatted">kubectl describe svc traefik --namespace kube-system</pre>



<figure class="wp-block-image"><img loading="lazy" decoding="async" width="1024" height="589" src="https://blog.richliu.com/wp-content/uploads/2019/10/image-6-1024x589.png" alt="" class="wp-image-4207" srcset="https://blog.richliu.com/wp-content/uploads/2019/10/image-6-1024x589.png 1024w, https://blog.richliu.com/wp-content/uploads/2019/10/image-6-300x173.png 300w, https://blog.richliu.com/wp-content/uploads/2019/10/image-6-768x442.png 768w, https://blog.richliu.com/wp-content/uploads/2019/10/image-6.png 1081w" sizes="(max-width: 1024px) 100vw, 1024px" /></figure>



<p>It can see a http hosted on 10.44.0.2 , add 10.44.0.2 daskboard-traefik.techarea.org to browser PC&#8217;s hosts file, it can use browser to access traefik dashboard . </p>



<figure class="wp-block-image"><img loading="lazy" decoding="async" width="1024" height="550" src="https://blog.richliu.com/wp-content/uploads/2019/10/image-7-1024x550.png" alt="" class="wp-image-4208" srcset="https://blog.richliu.com/wp-content/uploads/2019/10/image-7-1024x550.png 1024w, https://blog.richliu.com/wp-content/uploads/2019/10/image-7-300x161.png 300w, https://blog.richliu.com/wp-content/uploads/2019/10/image-7-768x413.png 768w" sizes="(max-width: 1024px) 100vw, 1024px" /></figure>



<p></p>



<h3 class="wp-block-heading">Create a nginx web site </h3>



<p>In here, we create three nginx website, and assigned a external ip address, it will also assign a domain name, traefik will have load balance traffic to all three pods. <br /><br />First create a new file called nginx.yaml </p>



<pre class="wp-block-code"><code>apiVersion: apps/v1
kind: Deployment
metadata:
  name: nginx
spec:
  selector:
    matchLabels:
      app: nginx
  replicas: 4
  template:
    metadata:
      labels:
        app: nginx
    spec:
      containers:
      - name: nginx
        image: nginx:1
        ports:
        - name: http
          containerPort: 80

---
apiVersion: v1
kind: Service
metadata:
  name: nginx
spec:
  ports:
  - name: http
    port: 80
    protocol: TCP
    targetPort: 80
  selector:
    app: nginx
  type: LoadBalancer
---
apiVersion: extensions/v1beta1
kind: Ingress
metadata:
  annotations:
    kubernetes.io/ingress.class: traefik
    traefik.ingress.kubernetes.io/rule-type: "PathPrefixStrip"
  name: nginx
spec:
  rules:
  - host: nginx.techarea.org
    http:
      paths:
      - path: /
        backend:
          serviceName: nginx
          servicePort: 80
</code></pre>



<p>replicas means how many pods you went to create, in here, we used 3, it will create 3 pods on clients. <br />host means url, in here is nginx.techarea.org. <br /><br />used kubectl to apply it. </p>



<pre class="wp-block-preformatted">kubectl apply -f nginx.yaml </pre>



<figure class="wp-block-image"><img loading="lazy" decoding="async" width="948" height="114" src="https://blog.richliu.com/wp-content/uploads/2019/10/image-3.png" alt="" class="wp-image-4203" srcset="https://blog.richliu.com/wp-content/uploads/2019/10/image-3.png 948w, https://blog.richliu.com/wp-content/uploads/2019/10/image-3-300x36.png 300w, https://blog.richliu.com/wp-content/uploads/2019/10/image-3-768x92.png 768w" sizes="(max-width: 948px) 100vw, 948px" /></figure>



<p>Get current service status </p>



<figure class="wp-block-image"><img loading="lazy" decoding="async" width="1024" height="101" src="https://blog.richliu.com/wp-content/uploads/2019/10/image-4-1024x101.png" alt="" class="wp-image-4204" srcset="https://blog.richliu.com/wp-content/uploads/2019/10/image-4-1024x101.png 1024w, https://blog.richliu.com/wp-content/uploads/2019/10/image-4-300x30.png 300w, https://blog.richliu.com/wp-content/uploads/2019/10/image-4-768x76.png 768w, https://blog.richliu.com/wp-content/uploads/2019/10/image-4.png 1187w" sizes="(max-width: 1024px) 100vw, 1024px" /></figure>



<p>We can see external ip is 192.168.110.80, add 192.168.110.80 nginx.techarea.org to your browser PC&#8217;s host file, and used browser to access nginx.techarea.org, it can see welcome nginx.  </p>



<figure class="wp-block-image"><img loading="lazy" decoding="async" width="1024" height="562" src="https://blog.richliu.com/wp-content/uploads/2019/10/image-5-1024x562.png" alt="" class="wp-image-4206" srcset="https://blog.richliu.com/wp-content/uploads/2019/10/image-5-1024x562.png 1024w, https://blog.richliu.com/wp-content/uploads/2019/10/image-5-300x165.png 300w, https://blog.richliu.com/wp-content/uploads/2019/10/image-5-768x421.png 768w, https://blog.richliu.com/wp-content/uploads/2019/10/image-5.png 1866w" sizes="(max-width: 1024px) 100vw, 1024px" /></figure>



<h3 class="wp-block-heading">Test Load Balance</h3>



<p>Now we finished install traefik and metallb successfully, next step is to verified does that really work ?<br /><br />it can use another host to run ab (apache benchmark to do this test) and used htop observe CPU loading.  <br /><br />Following is example to test nginx, if don&#8217;t see all CPU has loading, try to increase pods instance, like 4 . </p>



<pre class="wp-block-preformatted">ab -n 1000000 -c 400 -k http://nginx.techarea.org/</pre>



<pre class="wp-block-preformatted">Below is example result for nginx load balance. </pre>



<figure class="wp-block-image"><img loading="lazy" decoding="async" width="1024" height="394" src="https://blog.richliu.com/wp-content/uploads/2019/10/image-9-1024x394.png" alt="" class="wp-image-4210" srcset="https://blog.richliu.com/wp-content/uploads/2019/10/image-9-1024x394.png 1024w, https://blog.richliu.com/wp-content/uploads/2019/10/image-9-300x115.png 300w, https://blog.richliu.com/wp-content/uploads/2019/10/image-9-768x295.png 768w" sizes="(max-width: 1024px) 100vw, 1024px" /></figure>



<p>See, that&#8217;s easy job, right ? </p>
<p>The post <a rel="nofollow" href="https://blog.richliu.com/2019/11/01/4197/arm64-kubernetes-nginx-traefik-ingress-load-balance/">ARM64 Kubernetes Nginx Traefik Ingress Load Balance</a> appeared first on <a rel="nofollow" href="https://blog.richliu.com">richliu&#039;s blog</a>.</p>
]]></content:encoded>
					
					<wfw:commentRss>https://blog.richliu.com/2019/11/01/4197/arm64-kubernetes-nginx-traefik-ingress-load-balance/feed/</wfw:commentRss>
			<slash:comments>0</slash:comments>
		
		
			</item>
		<item>
		<title>Install Kubernetes on ARM64 Ubuntu 18.04 (with QEMU)</title>
		<link>https://blog.richliu.com/2019/09/25/4160/install-kubernetes-on-arm64-ubuntu-18-04/</link>
					<comments>https://blog.richliu.com/2019/09/25/4160/install-kubernetes-on-arm64-ubuntu-18-04/#respond</comments>
		
		<dc:creator><![CDATA[richliu]]></dc:creator>
		<pubDate>Wed, 25 Sep 2019 03:39:36 +0000</pubDate>
				<category><![CDATA[Cloud]]></category>
		<category><![CDATA[Ubuntu]]></category>
		<category><![CDATA[18.04]]></category>
		<category><![CDATA[aarch64]]></category>
		<category><![CDATA[flannel. qemu]]></category>
		<category><![CDATA[k8s]]></category>
		<category><![CDATA[kubernetes]]></category>
		<category><![CDATA[ubuntu]]></category>
		<category><![CDATA[weave]]></category>
		<guid isPermaLink="false">https://blog.richliu.com/?p=4160</guid>

					<description><![CDATA[<p>Install Kubernetes on Ubuntu 18.04 is very easy now, bu [&#8230;]</p>
<p>The post <a rel="nofollow" href="https://blog.richliu.com/2019/09/25/4160/install-kubernetes-on-arm64-ubuntu-18-04/">Install Kubernetes on ARM64 Ubuntu 18.04 (with QEMU)</a> appeared first on <a rel="nofollow" href="https://blog.richliu.com">richliu&#039;s blog</a>.</p>
]]></description>
										<content:encoded><![CDATA[
<p>Install Kubernetes on Ubuntu 18.04 is very easy now, but only for x86 platform. If on ARM64 environment, it might have some other problem. <br />Some old article mentioned a lot of information but software version is too old for deploy a new version software. <br /><br />After a lot of time to have research, here is instruction for how to install Kubernetes on ARM64 Ubuntu 18.04</p>



<span id="more-4160"></span>



<h2 class="wp-block-heading">Environment</h2>



<p>Hardware : Ampere eMag Server with 128G RAM and 1T storage<br />Kubernetes master and nodes are running in QEMU image, so, we prepared three QEMU  ARM64 ubuntu 18.04 images for kubernetes running. It also can use two VM to run this demo. </p>



<h2 class="wp-block-heading">Prepare QEMU Image</h2>



<p>It can download Ubuntu bionic cloud image from Taiwan mirror site</p>



<pre class="wp-block-preformatted">wget http://ftp.yzu.edu.tw/Linux/ubuntu-cloud-images/bionic/current/bionic-server-cloudimg-arm64.img </pre>



<p>or international mirror site </p>



<pre class="wp-block-preformatted">https://cloud-images.ubuntu.com/bionic/current/bionic-server-cloudimg-arm64.img</pre>



<h4 class="wp-block-heading">Install Necessary Package  </h4>



<p>Run following command to install necessary packages . </p>



<pre class="wp-block-preformatted">apt install -y qemu-system-arm bridge-utils cloud-image-utils git qemu-efi</pre>



<h4 class="wp-block-heading">Increase QEMU image size</h4>



<pre class="wp-block-preformatted">qemu-img resize bionic-server-cloudimg-arm64.img +200G</pre>



<p>Create UEFI bios and nvram for qemu image boot. </p>



<pre class="wp-block-preformatted">dd if=/dev/zero of=flash0.img bs=1M count=64
dd if=/usr/share/qemu-efi/QEMU_EFI.fd of=flash0.img conv=notrunc
dd if=/dev/zero of=flash1.img bs=1M count=64</pre>



<p>Copy Image to three spare images </p>



<pre class="wp-block-preformatted">cp flash0.img flash0-1.img
cp flash0.img flash0-2.img 
cp flash0.img flash0-3.img 
cp flash1.img flash1-1.img
cp flash1.img flash1-2.img
cp flash1.img flash1-3.img
cp  bionic-server-cloudimg-arm64.img   bionic-server-cloudimg-arm64-1.img 
cp  bionic-server-cloudimg-arm64.img   bionic-server-cloudimg-arm64-2.img 
cp  bionic-server-cloudimg-arm64.img   bionic-server-cloudimg-arm64-3.img </pre>



<h2 class="wp-block-heading"> Set up bridge and network devices </h2>



<p>

We already install bridge-utils before, now, it should configure bridge devices.

</p>



<pre class="wp-block-preformatted"> mkdir -p /etc/qemu ; echo "allow br0" > /etc/qemu/bridge.conf </pre>



<p> Because there is only one network interface on machine, we should use this interface as bridge device, save text below (name nic-br.sh or what you like) and modify it to fit your environment. <br /></p>



<pre class="wp-block-preformatted">ORIGNIC=enP6p1s0
ip addr flush $ORIGINIC
brctl addbr br0
brctl addif br0 $ORIGINIC
ifconfig br0 up
ifconfig br0 192.168.110.1 netmask 255.255.0.0
route add default gw 192.168.1.1
echo nameserver 8.8.8.8 &gt;&gt; /etc/resolv.conf </pre>



<h2 class="wp-block-heading">Configure Hugepage On Host Site (Option)</h2>



<p>Due to previous research on dpdk runs on ARM64 server, so, configure hugepages here. But not necessary for run k8s environment. <br />You can ignore this part </p>



<h4 class="wp-block-heading"> Configure Line Kernel boot command </h4>



<p> It needs to reserve hugepages memory space for Linux kernel, it reserves 32 pages and each pages 1GB, total 32GB. Please modify /etc/default/grub , and add hugepagesz=1GB hugepages=32 to GRUB_CMDLINE_LINUX, ex: </p>



<pre class="wp-block-preformatted">GRUB_CMDLINE_LINUX="console=tty0 hugepagesz=1GB hugepages=32"</pre>



<p> then run foloowing command to update grub.cfg </p>



<pre class="wp-block-preformatted"> update-grub </pre>



<h4 class="wp-block-heading"> Mount hugetlbfs by default </h4>



<p>

If wants to use hugepage, it needs to mount hugetlbfs somewhere, we can create a directory, ex: /mnt/hugepages and mount hugetblsfs there by default.

</p>



<pre class="wp-block-preformatted">mkdir -p /mnt/hugepages 
echo "nodev   /mnt/hugepages                  hugetlbfs       defaults,pagesize=1G    0 0 none" &gt;&gt; /etc/fstab </pre>



<p>Now, please reboot to make huagpage works. </p>



<h2 class="wp-block-heading">Running QEMU</h2>



<p>Following is QEMU script, save it (ex: named run-qemu.sh). It can be more simplification, but this script would be more understand what different. </p>



<pre class="wp-block-preformatted">IMAGE1=bionic-server-cloudimg-arm64-1.img
sudo qemu-system-aarch64 -name vm1 \
         -machine virt,gic_version=3,accel=kvm,usb=off \
         -cpu host -m 8192 \
         -uuid d0000000-1111-1111-1111-11111aaaaaaa \
         -smp 12,sockets=1,cores=12,threads=1 \
         -nographic -nodefaults \
         -pflash flash0-1.img -pflash flash1-1.img \
         -drive file=$IMAGE1,if=none,id=disk1 \
         -device virtio-blk-device,scsi=off,drive=disk1,id=virtio-disk1,bootindex=1 \
         -netdev tap,id=net0,ifname=tap0 \
         -device virtio-net-device,netdev=net0,mac=52:54:00:11:11:11 \
         -mem-path /mnt/hugepages \
         -serial telnet::9001,server,nowait &gt; guest_log-1.txt 2&gt;&gt; guest_log-1.txt &amp;
IMAGE2=bionic-server-cloudimg-arm64-2.img
sudo qemu-system-aarch64 -name vm2 \
         -machine virt,gic_version=3,accel=kvm,usb=off \
         -cpu host -m 8192 \
         -uuid d0000000-2222-2222-2222-22222bbbbbbb \
         -smp 12,sockets=1,cores=12,threads=1 \
         -nographic -nodefaults \
         -pflash flash0-2.img -pflash flash1-2.img \
         -drive file=$IMAGE2,if=none,id=disk2 \
         -device virtio-blk-device,scsi=off,drive=disk2,id=virtio-disk1,bootindex=1 \
         -netdev tap,id=net2,ifname=tap1 \
         -device virtio-net-device,netdev=net2,mac=52:54:00:22:22:22 \
         -mem-path /mnt/hugepages \
         -serial telnet::9002,server,nowait &gt; guest_log-2.txt 2&gt;&gt; guest_log-2.txt &amp;
IMAGE3=bionic-server-cloudimg-arm64-3.img
sudo qemu-system-aarch64 -name vm3 \
         -machine virt,gic_version=3,accel=kvm,usb=off \
         -cpu host -m 8192 \
         -uuid d0000000-3333-3333-3333-33333ccccccc \
         -smp 12,sockets=1,cores=12,threads=1 \
         -nographic -nodefaults \
         -pflash flash0-3.img -pflash flash1-3.img \
         -drive file=$IMAGE3,if=none,id=disk3 \
         -device virtio-blk-device,scsi=off,drive=disk3,id=virtio-disk1,bootindex=1 \
         -netdev tap,id=net3,ifname=tap2 \
         -device virtio-net-device,netdev=net3,mac=52:54:00:33:33:33 \
         -mem-path /mnt/hugepages \
         -serial telnet::9003,server,nowait &gt; guest_log-3.txt 2&gt;&gt; guest_log-3.txt &amp;
sleep 5
brctl addif br0 tap0
brctl addif br0 tap1
brctl addif br0 tap2</pre>



<p>There are some parameters need to understand in QEMU script. <br /><br />-uuid d0000000-1111-1111-1111-11111aaaaaaa \<br /><br />this will assign a unique uuid for each VM, k8s needs different VM run with different uuid and MAC address. <br />It also can use command &#8220;uuidgen&#8221; to generate different uuid for each VM, but here just for debug so assign a &#8220;easy to read&#8221; uuid. <br /><br />-device virtio-net-device,netdev=net3,mac=52:54:00:33:33:33 \<br /><br />Assign a special mac address for VM, because for k8s internal communication, use the same mac address will cause problem, please configure different address before run qemu script. It not easy to modify it after first boot (with cloud image)<br /><br />* Notice, first number for mac address cannot be odd , it would cause problem. <br /><br />-mem-path /mnt/hugepages \<br /><br />Tell VM to use hugepage, if were not configure host with hugepage, please remove this line. </p>



<p>Now,  please run scripts </p>



<pre class="wp-block-preformatted">bash nic-br.sh
bash run-qemu.sh </pre>



<p>Now, it can use telnet to connect each VM&#8217;s console </p>



<pre class="wp-block-preformatted">telnet localhost 9001<br /># or <br />telnet localhost 9002<br /># or <br />telnet localhost 9003</pre>



<p>After system booted/initialed, if you cannot login, please &#8220;killall qemu-system-aarch64&#8221; and follow this article <a href="https://blog.richliu.com/2017/08/31/2165/change-ubuntu-cloud-image-password">Change Ubuntu Cloud Image Password</a> to change all images&#8217;s password.  <br /><br />Somehow, for recent cloud image, it cannot modify password before run qemu script.</p>



<h2 class="wp-block-heading">Install Kubernetes </h2>



<p>There are a lot of article to talk about how to install on Ubuntu, I choice one for reference : <a href="https://vitux.com/install-and-deploy-kubernetes-on-ubuntu/" target="_blank" rel="noopener">Install and Deploy Kubernetes on Ubuntu 18.04 LTS</a><br /><br />Below will shortly note install command here. </p>



<h4 class="wp-block-heading">Install Docker and Kubeadm on every node </h4>



<pre class="wp-block-preformatted">sudo apt update 
sudo apt -y upgrade 

# install and enable docker
sudo apt -y install docker.io 
sudo systemctl enable docker 
sudo systemctl start docker 

# Install k8s
sudo apt -y install apt-transport-https curl
curl -s https://packages.cloud.google.com/apt/doc/apt-key.gpg | sudo apt-key add 
sudo apt-add-repository "deb http://apt.kubernetes.io/ kubernetes-xenial main"
sudo apt update
sudo apt-get install kubeadm -y</pre>



<h4 class="wp-block-heading">Configure Network IP address (Optional)</h4>



<p> Update to you network environment, here we used fix ip address.<br /><br /> Add new record to /etc/hosts   </p>



<pre class="wp-block-preformatted">192.168.110.50     k8s-master
192.168.110.60     k8s-worker-node1
192.168.110.70     k8s-worker-node2</pre>



<p>Please modify /etc/netplan/50-cloud-init.yam, remove dhcp and add fix address. remember, each node has different IP.  Following is only for k8s-master. </p>



<pre class="wp-block-preformatted">network:
     ethernets:
         eth0:
<strong>             addresses: [192.168.110.50/16,]
             gateway4: 192.168.1.1
             nameservers:
                 addresses: [8.8.8.8,8.8.4.4]</strong>
             match:
                 macaddress: '52:54:00:11:11:11'
             set-name: eth0
     version: 2</pre>



<h4 class="wp-block-heading">Configure Host name </h4>



<p>Run following command on master node </p>



<pre class="wp-block-preformatted">sudo hostnamectl set-hostname  k8s-master</pre>



<p> Run following command on other nodes</p>



<pre class="wp-block-preformatted">sudo hostnamectl set-hostname   k8s-worker-node1 
sudo hostnamectl set-hostname   k8s-worker-node2</pre>



<h4 class="wp-block-heading">Disable swap (Option)</h4>



<p>if image is not from cloud image, default Linux enabled swap function, k8s doesn&#8217;t support it, please disable it manually on all nodes and remove swap mount in /etc/fstab. </p>



<pre class="wp-block-preformatted"> sudo swapoff -a </pre>



<h2 class="wp-block-heading">Configure Kubernetes</h2>



<p>Now, we can initial Kubernetes. Run following command</p>



<pre class="wp-block-preformatted"> sudo kubeadm init --pod-network-cidr=10.244.0.0/16 </pre>



<p>wait for few minutes, it will show some result like this </p>



<figure class="wp-block-image"><img loading="lazy" decoding="async" width="1024" height="749" src="https://blog.richliu.com/wp-content/uploads/2019/09/image-1024x749.png" alt="" class="wp-image-4172" srcset="https://blog.richliu.com/wp-content/uploads/2019/09/image-1024x749.png 1024w, https://blog.richliu.com/wp-content/uploads/2019/09/image-300x220.png 300w, https://blog.richliu.com/wp-content/uploads/2019/09/image-768x562.png 768w, https://blog.richliu.com/wp-content/uploads/2019/09/image.png 1398w" sizes="(max-width: 1024px) 100vw, 1024px" /></figure>



<p>Run following command to assign current account has right to access k8s. </p>



<pre class="wp-block-preformatted">mkdir -p $HOME/.kube
sudo cp -i /etc/kubernetes/admin.conf $HOME/.kube/config
sudo chown $(id -u):$(id -g) $HOME/.kube/config</pre>



<p>Run this command on another node(k8s-worker-node1 and k8s-worker-node2).</p>



<pre class="wp-block-preformatted">sudo kubeadm join 192.168.110.50:6443 --token 46c1oj.i00vyfyn027pgew9 \
     --discovery-token-ca-cert-hash sha256:ed05198cc603ae009a862477bacef329a9e9a2bedc4a040bc4731e6d5cf4f48e</pre>



<figure class="wp-block-image"><img loading="lazy" decoding="async" width="1024" height="737" src="https://blog.richliu.com/wp-content/uploads/2019/09/image-1-1024x737.png" alt="" class="wp-image-4174" srcset="https://blog.richliu.com/wp-content/uploads/2019/09/image-1-1024x737.png 1024w, https://blog.richliu.com/wp-content/uploads/2019/09/image-1-300x216.png 300w, https://blog.richliu.com/wp-content/uploads/2019/09/image-1-768x552.png 768w, https://blog.richliu.com/wp-content/uploads/2019/09/image-1.png 1204w" sizes="(max-width: 1024px) 100vw, 1024px" /></figure>



<p>Run get nodes command, it will show current status, the master node status is NotReady, but don&#8217;t worry, it will become Ready after add pod and CNI (container networking interface) plugin. </p>



<pre class="wp-block-preformatted">ubuntu@k8s-master:~$ kubectl get nodes
 NAME         STATUS     ROLES    AGE     VERSION
 k8s-master   NotReady   master   3m42s   v1.16.0</pre>



<p>This action is very import on ARM64 k8s platform, in other document, they told you use flannel or some other document told you used old flannel. all of them not work for me. Please instead flannel with weave net. <br />(Ref <a rel="noreferrer noopener" aria-label="Weave Net for NetworkPolicy (opens in a new tab)" href="https://kubernetes.io/docs/tasks/administer-cluster/network-policy-provider/weave-network-policy/" target="_blank">Weave Net for NetworkPolicy</a> and <a rel="noreferrer noopener" aria-label="CoreDNS is not starting on Ubuntu 18.04.Bionic Beaver #980 (opens in a new tab)" href="https://github.com/kubernetes/kubeadm/issues/980" target="_blank">CoreDNS is not starting on Ubuntu 18.04.Bionic Beaver #980</a>)<br />Run following command to install weave net </p>



<pre class="wp-block-preformatted">kubectl apply -f "https://cloud.weave.works/k8s/net?k8s-version=$(kubectl version | base64 | tr -d '\n')"</pre>



<figure class="wp-block-image"><img loading="lazy" decoding="async" width="1024" height="232" src="https://blog.richliu.com/wp-content/uploads/2019/09/image-2-1024x232.png" alt="" class="wp-image-4175" srcset="https://blog.richliu.com/wp-content/uploads/2019/09/image-2-1024x232.png 1024w, https://blog.richliu.com/wp-content/uploads/2019/09/image-2-300x68.png 300w, https://blog.richliu.com/wp-content/uploads/2019/09/image-2-768x174.png 768w, https://blog.richliu.com/wp-content/uploads/2019/09/image-2.png 1397w" sizes="(max-width: 1024px) 100vw, 1024px" /></figure>



<p> Use the following command to view the status of the network:</p>



<figure class="wp-block-image"><img loading="lazy" decoding="async" width="1024" height="330" src="https://blog.richliu.com/wp-content/uploads/2019/09/image-3-1024x330.png" alt="" class="wp-image-4176" srcset="https://blog.richliu.com/wp-content/uploads/2019/09/image-3-1024x330.png 1024w, https://blog.richliu.com/wp-content/uploads/2019/09/image-3-300x97.png 300w, https://blog.richliu.com/wp-content/uploads/2019/09/image-3-768x248.png 768w, https://blog.richliu.com/wp-content/uploads/2019/09/image-3-620x200.png 620w, https://blog.richliu.com/wp-content/uploads/2019/09/image-3.png 1398w" sizes="(max-width: 1024px) 100vw, 1024px" /></figure>



<p> Get nodes again. </p>



<figure class="wp-block-image"><img loading="lazy" decoding="async" width="1024" height="142" src="https://blog.richliu.com/wp-content/uploads/2019/09/image-4-1024x142.png" alt="" class="wp-image-4177" srcset="https://blog.richliu.com/wp-content/uploads/2019/09/image-4-1024x142.png 1024w, https://blog.richliu.com/wp-content/uploads/2019/09/image-4-300x42.png 300w, https://blog.richliu.com/wp-content/uploads/2019/09/image-4-768x107.png 768w, https://blog.richliu.com/wp-content/uploads/2019/09/image-4.png 1395w" sizes="(max-width: 1024px) 100vw, 1024px" /></figure>



<p>Great!! it works. </p>



<h2 class="wp-block-heading">MicroK8s</h2>



<p>If you think steps above are too complex and you would like to only run k8s on one machine, microk8s is a good friend for you, can run on ARM64 and very easy to use, just run command </p>



<p>sudo snap install microk8s</p>



<p>And just add a prefix &#8220;microk8s.&#8221; before k8s command, ex:</p>



<pre class="wp-block-preformatted">microk8s.kubectl get nodes</pre>



<figure class="wp-block-image"><img loading="lazy" decoding="async" width="854" height="133" src="https://blog.richliu.com/wp-content/uploads/2019/09/image-5.png" alt="" class="wp-image-4178" srcset="https://blog.richliu.com/wp-content/uploads/2019/09/image-5.png 854w, https://blog.richliu.com/wp-content/uploads/2019/09/image-5-300x47.png 300w, https://blog.richliu.com/wp-content/uploads/2019/09/image-5-768x120.png 768w" sizes="(max-width: 854px) 100vw, 854px" /></figure>



<p>See, it&#8217;s very easy to use. right?</p>
<p>The post <a rel="nofollow" href="https://blog.richliu.com/2019/09/25/4160/install-kubernetes-on-arm64-ubuntu-18-04/">Install Kubernetes on ARM64 Ubuntu 18.04 (with QEMU)</a> appeared first on <a rel="nofollow" href="https://blog.richliu.com">richliu&#039;s blog</a>.</p>
]]></content:encoded>
					
					<wfw:commentRss>https://blog.richliu.com/2019/09/25/4160/install-kubernetes-on-arm64-ubuntu-18-04/feed/</wfw:commentRss>
			<slash:comments>0</slash:comments>
		
		
			</item>
		<item>
		<title>Change Ubuntu Cloud Image Size</title>
		<link>https://blog.richliu.com/2018/08/25/2318/change-ubuntu-cloud-image-size/</link>
					<comments>https://blog.richliu.com/2018/08/25/2318/change-ubuntu-cloud-image-size/#respond</comments>
		
		<dc:creator><![CDATA[richliu]]></dc:creator>
		<pubDate>Sat, 25 Aug 2018 14:39:21 +0000</pubDate>
				<category><![CDATA[Cloud]]></category>
		<category><![CDATA[16.04]]></category>
		<category><![CDATA[cloud image]]></category>
		<category><![CDATA[kpartx]]></category>
		<category><![CDATA[parted]]></category>
		<category><![CDATA[resize]]></category>
		<category><![CDATA[ubuntu]]></category>
		<guid isPermaLink="false">https://blog.richliu.com/?p=2318</guid>

					<description><![CDATA[<p>Ubuntu Cloud Image Size 似乎各個版本的特性不太一樣, 而且似乎也要用不同的方式修改 I [&#8230;]</p>
<p>The post <a rel="nofollow" href="https://blog.richliu.com/2018/08/25/2318/change-ubuntu-cloud-image-size/">Change Ubuntu Cloud Image Size</a> appeared first on <a rel="nofollow" href="https://blog.richliu.com">richliu&#039;s blog</a>.</p>
]]></description>
										<content:encoded><![CDATA[<p>Ubuntu Cloud Image Size 似乎各個版本的特性不太一樣, 而且似乎也要用不同的方式修改 Image size</p>
<p><span id="more-2318"></span></p>
<p>一般 change image size 是用這個指令</p>
<p>$ sudo qemu-img resize $UBUNTUVERSION-server-cloudimg-$ARCH.img +50G0<br />
ex:</p>
<pre lang="bash">
$ sudo qemu-img resize xenial-server-cloudimg-amd64-uefi1.img +50G
</pre>
<p>將 qcow2 image format 變成 raw disk </p>
<pre lang="bash">
$ sudo qemu-img convert  xenial-server-cloudimg-amd64-uefi1.img xenial-server-cloudimg-amd64-uefi1.raw
</pre>
<p>之前測 ARM64 17.04 和 17.10 都會自動增加 partition size<br />
但是最近碰到 18.04 似乎不會. (Both X64 and ARM64)</p>
<p>如果碰到的是 16.04 要增加 partition size 有問題, 要用 parted 修改 (似乎 fdisk 和 gdisk 都有問題)<br />
ex:</p>
<pre lang="bash">
$ parted xenial-server-cloudimg-amd64-uefi1.raw
(parted) p
Model:  (file)
Disk /work/research/vm/1.raw: 56.0GB
Sector size (logical/physical): 512B/512B
Partition Table: gpt
Disk Flags:

Number  Start   End     Size    File system  Name  Flags
14      1049kB  5243kB  4194kB                     bios_grub
15      5243kB  116MB   111MB   fat32              boot, esp
 1      116MB   2361MB  2245MB  ext4

(parted) resizepart
Warning: Not all of the space available to /work/research/vm/1.raw appears to be used, you can fix the GPT to use
all of the space (an extra 104857600 blocks) or continue with the current setting?
parted: invalid token: 1

Partition number? 1
End?  [2361MB]? 56G
</pre>
<p>離開就會儲存</p>
<p>Ubuntu 16.04 的 cloud image 不知道為什麼 cloud-init 會無法結束, 如果不能接觸到 login 那 cloud image 也沒有用. </p>
<p>這時可以用另一個方式移除 cloud-init 相關的套件,<br />
1. 使用 kpartx 將 image 掛到 loop devices 如果沒有, 就先安裝 kpartx 套件</p>
<pre lang="bash">
$ sudo apt install kpartx 
</pre>
<p>2. mount partition (還有 proc, dev, sys)<br />
3. 移除 cloud 相關套件<br />
4. umount partition (要先 umount proc, dev, sys<br />
5. 移除 loop device<br />
6. convert raw file 到 qcow2 格式 </p>
<p>mount cloud image partition </p>
<pre lang="bash">
$ sudo kpartx -av xenial-server-cloudimg-amd64-uefi1.raw
add map loop0p1 (253:0): 0 109147673 linear 7:0 227328
add map loop0p14 (253:1): 0 8192 linear 7:0 2048
add map loop0p15 (253:2): 0 217088 linear 7:0 10240
</pre>
<p>loop0p1 就是我們要 mount 的 disk , (註: 有可能因系統不同, 所以會有其他的 device name)</p>
<p>mount disk</p>
<pre lang="bash">
$ sudo su
$ mkdir disk
$ mount /dev/mapper/loop0p1 disk 
$ cd disk
$ mount --bind /proc proc
$ mount --bind /dev dev
$ mount --bind /sys sys
$ cd ..
$ chroot disk 
</pre>
<p>移除 cloud-init 相關的套件</p>
<pre lang="bash">
$ dpkg  -l |grep cloud
ii  cloud-guest-utils                0.27-0ubuntu25.1                           all          cloud guest utilities
ii  cloud-init                       18.3-9-g2e62cb8a-0ubuntu1~16.04.2          all          Init scripts for cloud instances
ii  cloud-initramfs-copymods         0.27ubuntu1.5                              all          copy initramfs modules into root filesystem for later use
ii  cloud-initramfs-dyn-netconf      0.27ubuntu1.5                              all          write a network interface file in /run for BOOTIF
ii  ubuntu-cloudimage-keyring        2013.11.11                                 all          GnuPG keys of the Ubuntu Cloud Image builder

$ dpkg -r cloud-guest-utils  cloud-init cloud-initramfs-copymods  ubuntu-server
</pre>
<p>umount disk </p>
<pre lang="bash">
$ exit 
$ cd disk 
$ umount proc
$ umount dev
$ umount sys
$ cd ..
$ umount disk
</pre>
<p>最後將 raw disk image 轉成 qcow2 </p>
<pre lang="bash">
$ sudo qemu-img convert  xenial-server-cloudimg-amd64-uefi1.raw xenial-server-cloudimg-amd64-uefi1.img
</pre>
<p>這樣 16.04 開機就不會卡在 cloud init script 了. </p>
<p>The post <a rel="nofollow" href="https://blog.richliu.com/2018/08/25/2318/change-ubuntu-cloud-image-size/">Change Ubuntu Cloud Image Size</a> appeared first on <a rel="nofollow" href="https://blog.richliu.com">richliu&#039;s blog</a>.</p>
]]></content:encoded>
					
					<wfw:commentRss>https://blog.richliu.com/2018/08/25/2318/change-ubuntu-cloud-image-size/feed/</wfw:commentRss>
			<slash:comments>0</slash:comments>
		
		
			</item>
		<item>
		<title>unsupported configuration: CPU mode &#8216;host-model&#8217; for aarch64 kvm domain on aarch64 host is not supported by hypervisor</title>
		<link>https://blog.richliu.com/2017/10/18/2189/unsupported-configuration-cpu-mode-host-model-for-aarch64-kvm-domain-on-aarch64-host-is-not-supported-by-hypervisor/</link>
					<comments>https://blog.richliu.com/2017/10/18/2189/unsupported-configuration-cpu-mode-host-model-for-aarch64-kvm-domain-on-aarch64-host-is-not-supported-by-hypervisor/#respond</comments>
		
		<dc:creator><![CDATA[richliu]]></dc:creator>
		<pubDate>Wed, 18 Oct 2017 02:33:36 +0000</pubDate>
				<category><![CDATA[OpenStack]]></category>
		<category><![CDATA[aarch64]]></category>
		<category><![CDATA[arm64]]></category>
		<category><![CDATA[host-model]]></category>
		<category><![CDATA[ocata]]></category>
		<guid isPermaLink="false">https://blog.richliu.com/?p=2189</guid>

					<description><![CDATA[<p>應該改 nova.conf 將 [libvirt] 內的 cpu_mode 改成 host-passthrou [&#8230;]</p>
<p>The post <a rel="nofollow" href="https://blog.richliu.com/2017/10/18/2189/unsupported-configuration-cpu-mode-host-model-for-aarch64-kvm-domain-on-aarch64-host-is-not-supported-by-hypervisor/">unsupported configuration: CPU mode &#8216;host-model&#8217; for aarch64 kvm domain on aarch64 host is not supported by hypervisor</a> appeared first on <a rel="nofollow" href="https://blog.richliu.com">richliu&#039;s blog</a>.</p>
]]></description>
										<content:encoded><![CDATA[<p>應該改 nova.conf<br />
將 [libvirt] 內的<br />
cpu_mode 改成 host-passthrough</p>
<p>應該只有影響 ocata </p>
<p>Ref.<br />
<a href="https://docs.openstack.org/juno/config-reference/content/kvm.html" rel="noopener" target="_blank">OpenStack KVM</a></p>
<p><a href="https://bugs.launchpad.net/ubuntu/+source/libvirt/+bug/1673467" rel="noopener" target="_blank">[ocata] unsupported configuration: CPU mode &#8216;host-model&#8217; for aarch64 kvm domain on aarch64 host is not supported by hypervisor</a></p>
<p>程式解法<br />
<a href="https://git.openstack.org/cgit/openstack/charm-nova-compute/commit/?id=b5d9b18c0afd06b721d78bced96b4c6c19f77834" rel="noopener" target="_blank">aarch64: set default cpu_mode to host-passthrough</a></p>
<p>The post <a rel="nofollow" href="https://blog.richliu.com/2017/10/18/2189/unsupported-configuration-cpu-mode-host-model-for-aarch64-kvm-domain-on-aarch64-host-is-not-supported-by-hypervisor/">unsupported configuration: CPU mode &#8216;host-model&#8217; for aarch64 kvm domain on aarch64 host is not supported by hypervisor</a> appeared first on <a rel="nofollow" href="https://blog.richliu.com">richliu&#039;s blog</a>.</p>
]]></content:encoded>
					
					<wfw:commentRss>https://blog.richliu.com/2017/10/18/2189/unsupported-configuration-cpu-mode-host-model-for-aarch64-kvm-domain-on-aarch64-host-is-not-supported-by-hypervisor/feed/</wfw:commentRss>
			<slash:comments>0</slash:comments>
		
		
			</item>
		<item>
		<title>Ubuntu Cloud Image Taiwan Mirror Site</title>
		<link>https://blog.richliu.com/2017/10/17/2187/ubuntu-cloud-image-taiwan-mirror-site/</link>
					<comments>https://blog.richliu.com/2017/10/17/2187/ubuntu-cloud-image-taiwan-mirror-site/#respond</comments>
		
		<dc:creator><![CDATA[richliu]]></dc:creator>
		<pubDate>Tue, 17 Oct 2017 10:01:47 +0000</pubDate>
				<category><![CDATA[Cloud]]></category>
		<guid isPermaLink="false">https://blog.richliu.com/?p=2187</guid>

					<description><![CDATA[<p>每次都找不到, 備份一下 http://ftp.yzu.edu.tw/Linux/ubuntu-cloud-i [&#8230;]</p>
<p>The post <a rel="nofollow" href="https://blog.richliu.com/2017/10/17/2187/ubuntu-cloud-image-taiwan-mirror-site/">Ubuntu Cloud Image Taiwan Mirror Site</a> appeared first on <a rel="nofollow" href="https://blog.richliu.com">richliu&#039;s blog</a>.</p>
]]></description>
										<content:encoded><![CDATA[<p>每次都找不到, 備份一下</p>
<p>http://ftp.yzu.edu.tw/Linux/ubuntu-cloud-images/</p>
<p>The post <a rel="nofollow" href="https://blog.richliu.com/2017/10/17/2187/ubuntu-cloud-image-taiwan-mirror-site/">Ubuntu Cloud Image Taiwan Mirror Site</a> appeared first on <a rel="nofollow" href="https://blog.richliu.com">richliu&#039;s blog</a>.</p>
]]></content:encoded>
					
					<wfw:commentRss>https://blog.richliu.com/2017/10/17/2187/ubuntu-cloud-image-taiwan-mirror-site/feed/</wfw:commentRss>
			<slash:comments>0</slash:comments>
		
		
			</item>
		<item>
		<title>ARM64 Hugepage(HugeTLB) Size</title>
		<link>https://blog.richliu.com/2017/10/06/2179/arm64-hugepagehugetlb-size/</link>
					<comments>https://blog.richliu.com/2017/10/06/2179/arm64-hugepagehugetlb-size/#respond</comments>
		
		<dc:creator><![CDATA[richliu]]></dc:creator>
		<pubDate>Fri, 06 Oct 2017 05:35:47 +0000</pubDate>
				<category><![CDATA[Cloud]]></category>
		<category><![CDATA[Linux]]></category>
		<guid isPermaLink="false">https://blog.richliu.com/?p=2179</guid>

					<description><![CDATA[<p>ARM64 and x86 hugepage size are different. Debian/Ubunt [&#8230;]</p>
<p>The post <a rel="nofollow" href="https://blog.richliu.com/2017/10/06/2179/arm64-hugepagehugetlb-size/">ARM64 Hugepage(HugeTLB) Size</a> appeared first on <a rel="nofollow" href="https://blog.richliu.com">richliu&#039;s blog</a>.</p>
]]></description>
										<content:encoded><![CDATA[<p>ARM64 and x86 hugepage size are different. </p>
<p>Debian/Ubuntu ARM64 kernel (4KB Pagesize)<br />
Hugepage size is 2MB/1GB</p>
<p>64KB Pagesize, hugepage is 512MB.</p>
<p>x86_64<br />
2MB : (has PSE cpuinfo flag)<br />
1GB : (has PDPE1GB cpuinfo flag)</p>
<p>different configuration has different setting</p>
<p>ref.<br />
<a href="https://wiki.debian.org/Hugepages" target="_blank" rel="noopener">Hugepages</a></p>
<p>The post <a rel="nofollow" href="https://blog.richliu.com/2017/10/06/2179/arm64-hugepagehugetlb-size/">ARM64 Hugepage(HugeTLB) Size</a> appeared first on <a rel="nofollow" href="https://blog.richliu.com">richliu&#039;s blog</a>.</p>
]]></content:encoded>
					
					<wfw:commentRss>https://blog.richliu.com/2017/10/06/2179/arm64-hugepagehugetlb-size/feed/</wfw:commentRss>
			<slash:comments>0</slash:comments>
		
		
			</item>
		<item>
		<title>QEMU Share Directory with Host Without Networking</title>
		<link>https://blog.richliu.com/2017/09/25/2173/qemu-share-directory-with-host-without-networking/</link>
					<comments>https://blog.richliu.com/2017/09/25/2173/qemu-share-directory-with-host-without-networking/#respond</comments>
		
		<dc:creator><![CDATA[richliu]]></dc:creator>
		<pubDate>Mon, 25 Sep 2017 12:33:41 +0000</pubDate>
				<category><![CDATA[Cloud]]></category>
		<category><![CDATA[9p]]></category>
		<category><![CDATA[qemu]]></category>
		<category><![CDATA[share]]></category>
		<category><![CDATA[virtio]]></category>
		<guid isPermaLink="false">https://blog.richliu.com/?p=2173</guid>

					<description><![CDATA[<p>If Guest Support 9P and virtio. Add this line to QEMU c [&#8230;]</p>
<p>The post <a rel="nofollow" href="https://blog.richliu.com/2017/09/25/2173/qemu-share-directory-with-host-without-networking/">QEMU Share Directory with Host Without Networking</a> appeared first on <a rel="nofollow" href="https://blog.richliu.com">richliu&#039;s blog</a>.</p>
]]></description>
										<content:encoded><![CDATA[<p>If Guest Support 9P and virtio. </p>
<p>Add this line to QEMU command</p>
<pre lang="text">
-virtfs local,path=/path/to/share,mount_tag=host0,security_model=passthrough,id=host0
</pre>
<p>and in guest os, edit /etc/fstab and add</p>
<pre lang="text">
host0   /wherever    9p      trans=virtio,version=9p2000.L   0 0
</pre>
<p>ref.<br />
https://superuser.com/questions/628169/how-to-share-a-directory-with-the-host-without-networking-in-qemu</p>
<p>The post <a rel="nofollow" href="https://blog.richliu.com/2017/09/25/2173/qemu-share-directory-with-host-without-networking/">QEMU Share Directory with Host Without Networking</a> appeared first on <a rel="nofollow" href="https://blog.richliu.com">richliu&#039;s blog</a>.</p>
]]></content:encoded>
					
					<wfw:commentRss>https://blog.richliu.com/2017/09/25/2173/qemu-share-directory-with-host-without-networking/feed/</wfw:commentRss>
			<slash:comments>0</slash:comments>
		
		
			</item>
		<item>
		<title>Change Ubuntu Cloud Image Password</title>
		<link>https://blog.richliu.com/2017/08/31/2165/change-ubuntu-cloud-image-password/</link>
					<comments>https://blog.richliu.com/2017/08/31/2165/change-ubuntu-cloud-image-password/#respond</comments>
		
		<dc:creator><![CDATA[richliu]]></dc:creator>
		<pubDate>Thu, 31 Aug 2017 07:49:25 +0000</pubDate>
				<category><![CDATA[Cloud]]></category>
		<category><![CDATA[Ubuntu]]></category>
		<category><![CDATA[cloud]]></category>
		<category><![CDATA[image]]></category>
		<category><![CDATA[password]]></category>
		<category><![CDATA[ubuntu]]></category>
		<guid isPermaLink="false">https://blog.richliu.com/?p=2165</guid>

					<description><![CDATA[<p>Ubuntu cloud image is very good for deploy a simple qem [&#8230;]</p>
<p>The post <a rel="nofollow" href="https://blog.richliu.com/2017/08/31/2165/change-ubuntu-cloud-image-password/">Change Ubuntu Cloud Image Password</a> appeared first on <a rel="nofollow" href="https://blog.richliu.com">richliu&#039;s blog</a>.</p>
]]></description>
										<content:encoded><![CDATA[
<p>Ubuntu cloud image is very good for deploy a simple qemu image system.<br />But the image has it owns password and initial script. </p>



<span id="more-2165"></span>



<p>

If want to use it, it needs to add new username and password into it.<br />and remove some packages.Download cloud Image from ubuntu, ex: download Ubuntu Zesty Cloud Image

</p>



<pre class="wp-block-preformatted">wget https://cloud-images.ubuntu.com/zesty/current/zesty-server-cloudimg-arm64.img </pre>



<p>

If locate in Taiwan, there is Taiwan mirror site,http://ftp.yzu.edu.tw/Linux/ubuntu-cloud-images/, it would be fast then cloud-images.ubuntu.com

</p>



<pre class="wp-block-preformatted">wget http://ftp.yzu.edu.tw/Linux/ubuntu-cloud-images/zesty/current/zesty-server-cloudimg-arm64.img</pre>



<p> Zesty only has UEFI image, so, there is no -disk1 or -uefi postfix keyword. </p>



<p><strong>If used bionic (Ubuntu 18.04), if you found change password function doesn&#8217;t work. <br />Please shutdown this image (suppose run with QEMU) and run change password command again . <br /><br />Suppose that something modify password when booting on Ubuntu 18.04.</strong></p>



<p>Install backdoor-image package, this program can help to install new username and password into cloud image. </p>



<pre class="wp-block-preformatted"><del>apt install bzr qemu-utils  <br />bzr branch lp:~smoser/+junk/backdoor-image  </del></pre>



<pre class="wp-block-preformatted">sudo apt-get install -qy cloud-image-utils git
git clone https://gist.github.com/8c65b8771d5ab1d99c44c285323dfff6.git backdoor-image</pre>



<p>Add new password, but first account is not work for me most time, so, I would like to add new username and password. (note: please don&#8217;t use this as default password on business purpose. )</p>



<pre class="wp-block-preformatted">cd backdoor-image  
sudo ./backdoor-image --user ubuntu --password ubuntu --password-auth ../zesty-server-cloudimg-arm64.img 
sudo ./backdoor-image --user test --password 123456 --password-auth ../zesty-server-cloudimg-arm64.img </pre>



<p>After boot into virtual machine with this image,  it can remove unnecessary packages.</p>



<pre class="wp-block-preformatted">sudo apt remove cloud-initramfs-copymods cloud-init</pre>
<p>The post <a rel="nofollow" href="https://blog.richliu.com/2017/08/31/2165/change-ubuntu-cloud-image-password/">Change Ubuntu Cloud Image Password</a> appeared first on <a rel="nofollow" href="https://blog.richliu.com">richliu&#039;s blog</a>.</p>
]]></content:encoded>
					
					<wfw:commentRss>https://blog.richliu.com/2017/08/31/2165/change-ubuntu-cloud-image-password/feed/</wfw:commentRss>
			<slash:comments>0</slash:comments>
		
		
			</item>
		<item>
		<title>No valid host was found. There are not enough hosts available</title>
		<link>https://blog.richliu.com/2017/08/03/2157/no-valid-host-was-found-there-are-not-enough-hosts-available/</link>
					<comments>https://blog.richliu.com/2017/08/03/2157/no-valid-host-was-found-there-are-not-enough-hosts-available/#respond</comments>
		
		<dc:creator><![CDATA[richliu]]></dc:creator>
		<pubDate>Thu, 03 Aug 2017 00:33:55 +0000</pubDate>
				<category><![CDATA[OpenStack]]></category>
		<category><![CDATA[aarch64]]></category>
		<category><![CDATA[arm64]]></category>
		<category><![CDATA[libvirt]]></category>
		<category><![CDATA[openstack]]></category>
		<category><![CDATA[uefi]]></category>
		<guid isPermaLink="false">https://blog.richliu.com/?p=2157</guid>

					<description><![CDATA[<p>OpenStack Horization error message no valid host was fo [&#8230;]</p>
<p>The post <a rel="nofollow" href="https://blog.richliu.com/2017/08/03/2157/no-valid-host-was-found-there-are-not-enough-hosts-available/">No valid host was found. There are not enough hosts available</a> appeared first on <a rel="nofollow" href="https://blog.richliu.com">richliu&#039;s blog</a>.</p>
]]></description>
										<content:encoded><![CDATA[<p>OpenStack Horization error message<br />
<span id="more-2157"></span></p>
<pre lang="text">
no valid host was found. There are not enough hosts available.
Code
500
Details
File "/usr/lib/python2.7/dist-packages/nova/conductor/manager.py", 
line 526, in build_instances context, request_spec, filter_properties) File "/usr/lib/python2.7/dist-packages/nova/conductor/manager.py", 
line 597, in _schedule_instances hosts = self.scheduler_client.select_destinations(context, spec_obj) File "/usr/lib/python2.7/dist-packages/nova/scheduler/utils.py", 
line 371, in wrapped return func(*args, **kwargs) File "/usr/lib/python2.7/dist-packages/nova/scheduler/client/__init__.py", 
line 51, in select_destinations return self.queryclient.select_destinations(context, spec_obj) File "/usr/lib/python2.7/dist-packages/nova/scheduler/client/__init__.py", 
line 37, in __run_method return getattr(self.instance, __name)(*args, **kwargs) 
File "/usr/lib/python2.7/dist-packages/nova/scheduler/client/query.py", 
line 32, in select_destinations return self.scheduler_rpcapi.select_destinations(context, spec_obj) 
File "/usr/lib/python2.7/dist-packages/nova/scheduler/rpcapi.py", 
line 129, in select_destinations return cctxt.call(ctxt, 'select_destinations', **msg_args) 
File "/usr/lib/python2.7/dist-packages/oslo_messaging/rpc/client.py", 
line 169, in call retry=self.retry) 
File "/usr/lib/python2.7/dist-packages/oslo_messaging/transport.py", 
line 97, in _send timeout=timeout, retry=retry) 
File "/usr/lib/python2.7/dist-packages/oslo_messaging/_drivers/amqpdriver.py", 
line 458, in send retry=retry) File "/usr/lib/python2.7/dist-packages/oslo_messaging/_drivers/amqpdriver.py", 
line 449, in _send raise result
</pre>
<p>Possible reason</p>
<p>* if using cloud uefi image, it needs to install qemu-efi package in computer node, don&#8217;t know why it won&#8217;t install it automatically .<br />
   $ apt install qemu-efi<br />
* when add new UEFI image, it needs to add new meta data parameter in Horization<br />
   hw_firmware_type=uefi</p>
<p>if see </p>
<pre lang="text">
2017-08-01 14:02:13.612 2409 ERROR nova.compute.manager [instance: b334f0b3-ca9a-4f9a-b488-532dce00265a] libvirtError: unsupported configuration: logfile not supported in this QEMU binary
2017-08-01 14:02:13.612 2409 ERROR nova.compute.manager [instance: b334f0b3-ca9a-4f9a-b488-532dce00265a]
# Use the "logd" backend for handling stdout/stderr from QEMU processes.
</pre>
<p>Reason<br />
* Libvirt later version support new function, logd, it&#8217;s a new console log function, but ARM64 doesn&#8217;t support it. workaround solution is to disable it</p>
<p>Edit file /usr/lib/python2.7/dist-packages/nova/virt/libvirt/driver.py, find </p>
<pre lang="text">
MIN_LIBVIRT_VIRTLOGD = (1, 3, 3)
MIN_QEMU_VIRTLOGD = (2, 7, 0)
</pre>
<p>Replaced it with</p>
<pre lang="text">
MIN_LIBVIRT_VIRTLOGD = (9, 9, 9)
MIN_QEMU_VIRTLOGD = (9, 9, 9)
</pre>
<p>it can avoid to call libvirt logd function. </p>
<p>rm -f /usr/lib/python2.7/dist-packages/nova/virt/libvirt/driver.pyc, make sure it will call .py<br />
then, reboot service (or system)</p>
<p>Ref.<br />
http://dozencloud.org/ </p>
<p>The post <a rel="nofollow" href="https://blog.richliu.com/2017/08/03/2157/no-valid-host-was-found-there-are-not-enough-hosts-available/">No valid host was found. There are not enough hosts available</a> appeared first on <a rel="nofollow" href="https://blog.richliu.com">richliu&#039;s blog</a>.</p>
]]></content:encoded>
					
					<wfw:commentRss>https://blog.richliu.com/2017/08/03/2157/no-valid-host-was-found-there-are-not-enough-hosts-available/feed/</wfw:commentRss>
			<slash:comments>0</slash:comments>
		
		
			</item>
	</channel>
</rss>
