东东东 陈煜东的博客

月份存档: 七月 2013 ( 1 / 2)

[转]Linux epoll给我们带来什么

Q:网络服务器的瓶颈在哪? A:IO效率。

在大家苦苦的为在线人数的增长而导致的系统资源吃紧上的问题正在发愁的时候,Linux 2.6内核中提供的System Epoll为我们提供了一套完美的解决方案。传统的select以及poll的效率会因为在线人数的线形递增而导致呈二次乃至三次方的下降,这些直接导致了网络服务器可以支持的人数有了个比较明显的限制。

自从Linux提供了/dev/epoll的设备以及后来2.6内核中对/dev/epoll设备的访问的封装(System Epoll)之后,这种现象得到了大大的缓解,如果说几个月前,大家还对epoll不熟悉,那么现在来说的话,epoll的应用已经得到了大范围的普及。

那么究竟如何来使用epoll呢?其实非常简单。 通过在包含一个头文件#include <sys/epoll.h>以及几个简单的API将可以大大的提高你的网络服务器的支持人数。

首先通过create_epoll(int maxfds)来创建一个epoll的句柄,其中maxfds为你epoll所支持的最大句柄数。这个函数会返回一个新的epoll句柄,之后的所有操作将通过这个句柄来进行操作。在用完之后,记得用close()来关闭这个创建出来的epoll句柄。

之后在你的网络主循环里面,每一帧的调用epoll_wait(int epfd, epoll_event events, int max events, int timeout)来查询所有的网络接口,看哪一个可以读,哪一个可以写了。基本的语法为:

nfds = epoll_wait(kdpfd, events, maxevents, -1);

其中kdpfd为用epoll_create创建之后的句柄,events是一个epoll_event*的指针,当epoll_wait这个函数操作成功之后,epoll_events里面将储存所有的读写事件。max_events是当前需要监听的所有socket句柄数。最后一个timeout是epoll_wait的超时,为0的时候表示马上返回,为-1的时候表示一直等下去,直到有事件范围,为任意正整数的时候表示等这么长的时间,如果一直没有事件,则范围。一般如果网络主循环是单独的线程的话,可以用-1来等,这样可以保证一些效率,如果是和主逻辑在同一个线程的话,则可以用0来保证主循环的效率。

epoll_wait范围之后应该是一个循环,遍利所有的事件:

for(n = 0; n < nfds; ++n) {
    if(events[n].data.fd == listener) { //如果是主socket的事件的话,则表示有新连接进入了,进行新连接的处理。
        client = accept(listener, (struct sockaddr *) &local, &addrlen);
    if(client < 0){
        perror("accept");
        continue;
    }
    setnonblocking(client); // 将新连接置于非阻塞模式
    ev.events = EPOLLIN | EPOLLET; // 并且将新连接也加入EPOLL的监听队列。

注意,这里的参数EPOLLIN | EPOLLET并没有设置对写socket的监听,如果有写操作的话,这个时候epoll是不会返回事件的,如果要对写操作也监听的话,应该是EPOLLIN | EPOLLOUT | EPOLLET

ev.data.fd = client;
if (epoll_ctl(kdpfd, EPOLL_CTL_ADD, client, &ev) < 0) {
  // 设置好event之后,将这个新的event通过epoll_ctl加入到epoll的监听队列里面,这里用EPOLL_CTL_ADD来加一个新的epoll事件,
  //通过EPOLL_CTL_DEL来减少一个epoll事件,通过EPOLL_CTL_MOD来改变一个事件的监听方式。
    fprintf(stderr, "epoll set insertion error: fd=%d0, client);
    return -1;

} else {  // 如果不是主socket的事件的话,则代表是一个用户socket的事件,
         //则来处理这个用户socket的事情,比如说read(fd,xxx)之类的,或者一些其他的处理。
    do_use_fd(events[n].data.fd);
}

对,epoll的操作就这么简单,总共不过4个API:epoll_create, epoll_ctl, epoll_wait和close。 如果您对epoll的效率还不太了解,请参考我之前关于网络游戏的网络编程等相关的文章。

本文转载自:http://dev.gameres.com/Program/Control/Epoll.htm

声明:未经允许禁止转载 东东东 陈煜东的博客 文章,谢谢。如经授权,转载请注明: 转载自东东东 陈煜东的博客

本文链接地址: [转]Linux epoll给我们带来什么 – https://www.chenyudong.com/archives/linux-epoll-network-io.html

分类: 网络

修改重置MySQL的root密码

修改密码

简单点的,需改自己的密码,使用一下命令。

mysql> SET PASSWORD = PASSWORD('123456');
##或者
mysql> SET PASSWORD FOR 'root'@'localhost' = PASSWORD('新密码');  

修改其他用户的密码

mysql> UPDATE mysql.user SET password=PASSWORD('新密码') WHERE User='root';
mysql> FLUSH PRIVILEGES;

这是忘记root密码的情况,重置密码

第一步,停止mysql服务器运行,关闭mysqld,接下里重新启动mysqld,使用以下命令

mysqld --skip-grant-tables

添加这个参数可以让任何人不用密码就能连接mysql数据库,并且获得任何权限。因为这个是不安全的,可以添加一个参数--skip-networking阻止远程连接。即以下代码启动mysql服务器

mysqld --skip-grant-tables --skip-networking

PS. 如果出现

160803 15:50:21 [Warning] The syntax 'for replication startup options' is deprecated and will be removed in MySQL 6.0. Please use 'CHANGE MASTER' instead.
160803 15:50:21 [ERROR] Fatal error: Please read "Security" section of the manual to find out how to run mysqld as root!

160803 15:50:21 [ERROR] Aborting

160803 15:50:21 [Note] ./mysqld: Shutdown complete

加上参数--user=root

mysqld --skip-grant-tables --skip-networking --user=root

第二步,使用mysql客户端访问mysql服务器,接下来运行sql语句更改root的密码。

mysql> UPDATE mysql.user SET Password=PASSWORD('MyNewPass')  WHERE User='root';
mysql> FLUSH PRIVILEGES;

FLUSH语句是告诉服务器去重新加载表的权限到内存中,确保密码已经更改生效。

第三步,现在你已经可以使用root帐号和新密码去连接mysql服务器了。所以现在要停止mysql服务器,然后使用正常的参数启动mysql。例如,

mysqld --console
##或者
/etc/init.d/mysql start

只要不带参数--skip-grant-tables--skip-networking就行了

声明:未经允许禁止转载 东东东 陈煜东的博客 文章,谢谢。如经授权,转载请注明: 转载自东东东 陈煜东的博客

本文链接地址: 修改重置MySQL的root密码 – https://www.chenyudong.com/archives/reset-mysql-root-password.html

分类: 网站建设

libvirt 问题解决记录集

本篇记录在使用libvirt的时候遇到的一些情况,即解决方法.

出现Permission denied

[root@localhost vm]# virsh start centos
error: Failed to start domain centos
error: internal error process exited while connecting to monitor: qemu-system-x86_64: -drive file=/home/d/shixun/vm/vdisk.img,if=none,id=drive-ide0-0-0,format=qcow2: could not open disk image /home/d/shixun/vm/vdisk.img: Permission denied

解决:/etc/libvirt/qemu.conf

# Some examples of valid values are:
#
# user = "qemu" # A user named "qemu"
# user = "+0" # Super user (uid=0)
# user = "100" # A user named "100" or a user with uid=100
#
user = "root"

# The group for QEMU processes run by the system instance. It can be
# specified in a similar way to user.
group = "root"

# Whether libvirt should dynamically change file ownership
# to match the configured user/group above. Defaults to 1.
# Set to 0 to disable file ownership changes.
dynamic_ownership = 0

我的这个没能解决问题

/etc/init.d/libvirtd restart 不管用

libvirt遇到死锁

在使用virsh对虚拟机进行动态迁移时,虚拟机没有开启.于是就去开启虚拟机,但是却发现无法运行.

Error starting domain: Timed out during operation: cannot acquire state change lock

libvirtError: Timed out during operation: cannot acquire state change lock

我进行了以下的步骤

virsh undefine centos

####Login as a root user and kill the libvirtd.

killall -9 libvirtd

rm /var/run/libvirtd.pid   ##### Remove the libvirtd pid file.

/etc/init.d/libvirtd  restart   #### Restart libvirtd.

在尝试上面的操作后,不起作用.

修改一下的domain的xml文件中的name标签,给虚拟机改个名字,期间我还删除了domain的xml文件里的qemu:commandline里面信息,重新define后就可以运行了.

迁移需要FQDN

在进行迁移的时候使用命令 virsh migrate –live ubuntu qemu+ssh://dest_ip/system

error: internal hostname on destination resolved to localhost, but migration requires an FQDN

解决:ssh进入到dest host机器,运行hostname domain 就好了.其中domian是一个域名.将接下来就可以进行迁移了.

启动nfs出现问题

启动NFS服务,出现问题

Failed to issue method call: Unit nfsserver.service failed to load: No such file or directory. See system logs and 'systemctl status nfsserver.service' for details.

解决:按照教程来就好了

# vim /etc/exports
/var/lib/libvirt/images *.example.com(rw,no_root_squash,sync)

# service nfs start

# mount -t nfs storage_host:/var/lib/libvirt/images /var/lib/libvirt/images

挂载nfs出现问题

当去mount远程的nfs服务器,出现问题了.

mount.nfs: access denied by server while mounting 211.87.***.53:/mnt/nfs

解决:原来发现,在/etc/exports中,没有将/mnt/nfs添加进去,只能将里面有的文件夹才能mount到本机来.

可以先umoutn /mnt/nfs ,然后在mount看看能否成功

virsh关闭虚拟机

virsh shutdown 关闭虚拟机没起作用

解决:需要在虚拟机里安装一些东西

yum install acpid
chkconfig acpid on
service acpid start

virsh无法使用ssh协议访问远程机器

当我去远程查询信息的时候,virsh -c qemu+ssh://211.87.***.88/system list 的时候出现了下面的问题.

error: failed to connect to the hypervisor
error: no valid connection
error: End of file while reading data: : Input/output error

查看日志 cat /var/log/secure | grep sshd 发现是我这里主动发出断开的.难道是检测到libvirtd有些问题导致的?

当时使用virt-manage可以查询到远程的信息.估计是sshd出现的问题把.

解决:我没有重新安装sshd,我是通过tcp协议进行迁移的,因为是做测试,所以没有考虑安全的问题.具体使用tcp进行迁移,查看virsh使用qemu+tcp访问远程libvirtd .

声明:未经允许禁止转载 东东东 陈煜东的博客 文章,谢谢。如经授权,转载请注明: 转载自东东东 陈煜东的博客

本文链接地址: libvirt 问题解决记录集 – https://www.chenyudong.com/archives/libvirt-problem-and-resolution.html

分类: 虚拟化

virsh对kvm虚拟机进行动态迁移

迁移的类型:静态迁移和动态迁移

迁移虚拟机的方式有两种:一种是动态迁移,一种是静态迁移。

静态迁移

静态迁移:也叫做常规迁移、离线迁移(Offline Migration)。就是在虚拟机关机暂停的情况下从一台物理机迁移到另一台物理机。因为虚拟机的文件系统建立在虚拟机镜像上面,所以在虚拟机关机的情况下,只需要简单的迁移虚拟机镜像和相应的配置文件到另外一台物理主机上;如果需要保存虚拟机迁移之前的状态,在迁移之前将虚拟机暂停,然后拷贝状态至目的主机,最后在目的主机重建虚拟机状态,恢复执行。这种方式的迁移过程需要显式的停止虚拟机的运行。从用户角度看,有明确的一段停机时间,虚拟机上的服务不可用。这种迁移方式简单易行,适用于对服务可用性要求不严格的场合。

动态迁移

动态迁移(Live Migration):也叫在线迁移(Online Migration)。就是在保证虚拟机上服务正常运行的同时,将一个虚拟机系统从一个物理主机移动到另一个物理主机的过程。该过程不会对最终用户造成明显的影响,从而使得管理员能够在不影响用户正常使用的情况下,对物理服务器进行离线维修或者升级。与静态迁移不同的是,为了保证迁移过程中虚拟机服务的可用,迁移过程仅有非常短暂的停机时间。迁移的前面阶段,服务在源主机的虚拟机上运行,当迁移进行到一定阶段,目的主机已经具备了运行虚拟机系统的必须资源,经过一个非常短暂的切换,源主机将控制权转移到目的主机,虚拟机系统在目的主机上继续运行。对于虚拟机服务本身而言,由于切换的时间非常短暂,用户感觉不到服务的中断,因而迁移过程对用户是透明的。动态迁移适用于对虚拟机服务可用性要求很高的场合。

动态迁移需要将原有的虚拟机镜像放在采用 SAN(storage area network)或 NAS(network-attached storage)之类的集中式共享外存设备,这样迁移的时候,不是迁移整个硬盘镜象,而是迁移内存的信息.所以迁移起来,速度比较快,停顿时间少。

动态迁移实际上是把虚拟机的配置封装在一个文件中,然后通过高速网络,把虚拟机配置和内存运行状态从一台物理机迅速传送到另外一台物理机上,期间虚拟机一直保持运行状态。现有技术条件下,大多虚拟机软件如 VMware、Hyper-V、Xen 进行动态迁移都需要共享存储的支持。典型的共享存储包括 NFS 和 SMB/CIFS 协议的网络文件系统,或者通过 iSCSI 连接到 SAN 网络。选用哪一种网络文件系统,需要根据具体情况而定。本文的实验采用了 NFS 文件系统作为源主机和目的主机之间的共享存储。

使用nfs网络文件系统

source host和dest host都通过网卡和NFS server进行连接,所有的VM镜像都在NFS Server上,然后将VM1从source host迁移到dest host上,通过网络来进行迁移,所以网络的速度决定这迁移的快慢.

nfs配置

 修改文件vi /etc/exports
/home/images *(rw,sync,no_root_squash)
/home/images 为要共享的文件夹
 rw:可读写的权限;
 ro:只读的权限;
 no_root_squash:登入到 NFS 主机的用户如果是 ROOT 用户,他就拥有 ROOT 权限,此参数很不安全,建议不要使用。
 sync:资料同步写入存储器中。
 async:资料会先暂时存放在内存中,不会直接写入硬盘。

重新启动 nfsserver 服务
 # service nfsserver restart 或者 systemctl restart nfs-server.service

查看状态
systemctl status nfs-server.service   ####查看nfs-server状态
exportfs -av   #####如果显示出共享的文件夹的话,说明设置已经生效

挂载NFS-server共享网络存储到本机
mount -t  nfs  nfs-server-host:/home/images /mnt/nfs
将NFS-server上的存储器/home/images/ 挂载到本地的/mnt/nfs 文件夹下。

nfs可能遇到的问题

如果在挂载nfs的时候,按tab键无法补全路径.

那么是防火墙的原因,把它添加到允许的规则里。设置selinux

setsebool -P virt_use_nfs 1

权限拒绝

error: Failed to start domain vdisk
error: internal error Process exited while reading console log output: char device redirected to /dev/pts/1
qemu-system-x86_64: -drive file=/mnt/nfs/vdisk.img,if=none,id=drive-ide0-0-0,format=qcow2: could not open disk image /mnt/nfs/vdisk.img: Permission denied

设置/mnt/nfs/vdisk.img的权限

注意问题

一定要注意所要共享的目录的权限问题,包括它的父目录,这些目录的权限要一样,否则mount的时候会出错

另外这个镜像最好都方在一个位置下。比如将nfs挂载到source host在/mnt/nfs,那么最好也在dest host的/mnt/nfs,路径一样,这样将来迁移就比较方便了。增加迁移的成功率。而且使用virt-manage必须路径一直,virsh可以要求不一致。只好还是source host和dest host在相同的路径挂载NFS网络共享系统

进行迁移

启动虚拟机

在 source host主机启动虚拟机

virsh start vdisk    ####vdisk 为虚拟机的名字

查看虚拟机状态

# virsh list --all
 Id    名称                            状态
----------------------------------------------------
 1     centos                         running
 2     vdisk                          running

进行迁移

virsh migrate vdisk --live qemu+ssh://des_ip:/system --unsafe

稍微过一会儿,我们就可以在dest host目标主机上看到虚拟机正在运行了。

参考资料

声明:未经允许禁止转载 东东东 陈煜东的博客 文章,谢谢。如经授权,转载请注明: 转载自东东东 陈煜东的博客

本文链接地址: virsh对kvm虚拟机进行动态迁移 – https://www.chenyudong.com/archives/virsh-kvm-live-migration-with-libvirt.html

分类: 虚拟化

使用virsh创建虚拟机

第一步,先新建一块虚拟硬盘,这个不多说了,看之前的资料有

第二步,新建一个xml文件,里面存放虚拟机的配置信息,有内存、cpu、硬盘位置、光驱、VNC等配置,我们先贴出一个demo,下载该文件

<domain type="kvm">
    <name>centos</name>  <!--虚拟机名称-->
    <memory unit="MiB">1024</memory>   <!--最大内存,单位k-->
    <currentMemory unit="MiB">1024</currentMemory>  <!--可用内存,单位k-->
    <vcpu>2</vcpu>   <!--//虚拟cpu个数-->
    <os>
        <type arch="x86_64" machine="pc">hvm</type>
        <boot dev="hd" /> <!-- 硬盘启动 -->
        <boot dev="cdrom" />     <!--//光盘启动-->
    </os>
    <features>
        <acpi />
        <apic />
        <pae />
    </features>
    <clock offset="localtime" />
    <on_poweroff>destroy</on_poweroff>
    <on_reboot>restart</on_reboot>
    <on_crash>destroy</on_crash>
    <devices>
        <emulator>/usr/libexec/qemu-kvm</emulator>
        <disk type="file" device="disk">
            <driver name="qemu" type="qcow2" />
            <source file="/var/lib/libvirt/images/test.qcow2" />        <!--目的镜像路径-->
            <target dev="hda" bus="ide" />
        </disk>
        <disk type="file" device="cdrom">
            <source file="/var/lib/libvirt/images/ubuntu.iso" />        <!--光盘镜像路径 -->
            <target dev="hdb" bus="ide" />
        </disk>
        <interface type="bridge">       <!--虚拟机网络连接方式-->
            <source bridge="br0" />      <!--当前主机网桥的名称-->
        </interface>
        <input type="mouse" bus="ps2" />
        <!--vnc方式登录,端口号自动分配,自动加1,可以通过virsh vncdisplay来查询-->
        <graphics type="vnc" port="-1" autoport="yes" listen="0.0.0.0" keymap="en-us" />
    </devices>
</domain>

创建虚拟机

virsh define centos.xml   ###将配置导入到虚拟机
virsh start centos    #### 启动虚拟机

声明:未经允许禁止转载 东东东 陈煜东的博客 文章,谢谢。如经授权,转载请注明: 转载自东东东 陈煜东的博客

本文链接地址: 使用virsh创建虚拟机 – https://www.chenyudong.com/archives/virsh-create-vm-with-libvirt.html

分类: 虚拟化

qemu和libvirt在pci pass through下动态迁移失败

最近的项目是虚拟机在PCI pass-through下做动态迁移,目前还没有一个好的解决方案,需要我们小组去讨论并提出一个解决方案来.既然是要做PCI pass through下做动态迁移的解决方案,那就得要先在这样的情况下做个迁移,看看到底会出现什么样的问题.

方案一:使用virsh进行动态迁移

在前面的文章中,我们进行的虚拟机的pci pass through,如果对pci pass through有不会的地方,参考之前的文章来进行设置.

接下来,我们要进行虚拟机的动态迁移.使用virsh启动虚拟机,运行以下命令进行迁移

virsh migrate --live vdisk qemu+ssh://211.87.***.45/system --unsafe

运行完后会出现问题.报了一个这样的错误.

error: Requested operation is not valid: domain has assigned non-USB host devices

上面的错误说明,现在的请求操作的非法的,因为虚拟机使用了非USB设备.

可以看到libvirt的源码 src/qemu/qemu_migration.c

/* Validate whether the domain is safe to migrate.  If vm is NULL,
 * then this is being run in the v2 Prepare stage on the destination
 * (where we only have the target xml); if vm is provided, then this
 * is being run in either v2 Perform or v3 Begin (where we also have
 * access to all of the domain's metadata, such as whether it is
 * marked autodestroy or has snapshots).  While it would be nice to
 * assume that checking on source is sufficient to prevent ever
 * talking to the destination in the first place, we are stuck with
 * the fact that older servers did not do checks on the source. */
bool
qemuMigrationIsAllowed(virQEMUDriverPtr driver, virDomainObjPtr vm,
                       virDomainDefPtr def, bool remote, bool abort_on_error)
{
    int nsnapshots;
    int pauseReason;
    bool forbid;
    size_t i;

    if (vm) {
        if (qemuProcessAutoDestroyActive(driver, vm)) {
            virReportError(VIR_ERR_OPERATION_INVALID,
                           "%s", _("domain is marked for auto destroy"));
            return false;
        }

        /* perform these checks only when migrating to remote hosts */
        if (remote) {
            nsnapshots = virDomainSnapshotObjListNum(vm->snapshots, NULL, 0);
            if (nsnapshots < 0)
                return false;

            if (nsnapshots > 0) {
                virReportError(VIR_ERR_OPERATION_INVALID,
                               _("cannot migrate domain with %d snapshots"),
                               nsnapshots);
                return false;
            }

            /* cancel migration if disk I/O error is emitted while migrating */
            if (abort_on_error &&
                virDomainObjGetState(vm, &pauseReason) == VIR_DOMAIN_PAUSED &&
                pauseReason == VIR_DOMAIN_PAUSED_IOERROR) {
                virReportError(VIR_ERR_OPERATION_INVALID, "%s",
                               _("cannot migrate domain with I/O error"));
                return false;
            }

        }

        if (virDomainHasDiskMirror(vm)) {
            virReportError(VIR_ERR_OPERATION_INVALID, "%s",
                           _("domain has an active block job"));
            return false;
        }

        def = vm->def;
    }

    /* Migration with USB host devices is allowed, all other devices are
     * forbidden.
     */
    forbid = false;
    for (i = 0; i < def->nhostdevs; i++) {
        virDomainHostdevDefPtr hostdev = def->hostdevs[i];
        if (hostdev>mode != VIR_DOMAIN_HOSTDEV_MODE_SUBSYS ||
            hostdev->source.subsys.type != VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_USB) {
            forbid = true;
            break;
        }
    }
    if (forbid) {
        virReportError(VIR_ERR_OPERATION_INVALID,"%s",
                       _("domain has assigned non-USB host devices"));
        return false;
    }

    return true;
}

可以看到源码上显示,只要检测到虚拟机上使用了非USB的PCI设备,直接将borbid设置为true,禁止虚拟机的迁移.

如果要添加可以迁移的PCI设备,那么需要在这里进行相应的修改.

方案二:使用qemu进行动态迁移

在source host运行以下命令以启动虚拟机

/usr/bin/qemu-kvm -name vdisk -enable-kvm -m 512 -smp 2 
-hda /mnt/nfs/vdisk.img 
-monitor stdio 
-vnc 0.0.0.0:0 
-device pci-assign,host=00:1b.0

在dest host上运行以下命令,等待虚拟机的迁移:

/usr/bin/qemu-kvm -name vdisk -enable-kvm -m 512 -smp 2 
-hda /mnt/nfs/vdisk.img 
-monitor stdio 
-vnc 0.0.0.0:0 
-incoming tcp:0.0.0.0:8888
  • 参数-incoming tcp:0.0.0.0:8888说明的是,虚拟机在监听tcp的8888端口,等待源虚拟机被迁移过来.

此时虚拟机的状态是inmigration状态,等待被迁移过来.

在source host上输入以下命令,进行虚拟机的迁移.

(qemu) migrate -d -b tcp:dest_ip:8888

 -d 可以在迁移的过程中查询迁移状态,否则只能在迁移结束后查询。
 -b 迁移虚拟机存储文件
 tcp:dest_ip:8888 数据迁移的协议、目的主机和端口。协议和端口必须和目的主机上虚拟机的 -incoming 参数一致。

运行这个命令后,出报这样的错误

(qemu) migrate -d tcp:dest_ip:8888
migrate: State blocked by non-migratable device '0000:00:04.0/pci-assign'

应该也是进行了检查,使用了一个不可迁移设备即pci pass through的设备.

通过libvirt和qemu的动态迁移出先的问题,基本可以定位到相应的代码,那么只要提供一种相应的解决方案,那么就可以迁移其他的设备了.

声明:未经允许禁止转载 东东东 陈煜东的博客 文章,谢谢。如经授权,转载请注明: 转载自东东东 陈煜东的博客

本文链接地址: qemu和libvirt在pci pass through下动态迁移失败 – https://www.chenyudong.com/archives/live-migrate-with-pci-pass-through-fail-with-libvirt-and-qemu.html

分类: 虚拟化

域(Domains) 客户机(Guests) 虚拟机(Virtual Machines)区别

术语域 (domain)客户机 (guest)虚拟机 (virtual machine)经常被交换使用的.但是他们还是有细微的区别的.

域 (domain) 是一组可配置的资源集合,包括内存,虚拟CPU,网络设备,存储设备,这些配置都是虚拟机 (virtual machine)运行的时候使用的.域 (Domain)被独立地赋予了虚拟资源(virtual resources),并且可以启动(start)、停止(stop)、重启(restart).

如果你使用过libvirt,那么你应该知道有个domain XML文件,回忆一下里面是记录着什么?是资源的信息吧.有CPU,内存,硬盘,光驱,网络,还有PCI上的设备.

客户机 (Guest)是一个运行在domain之内的虚拟化操作系统.也可以叫Guest OS,它可以是半虚拟化或者是硬件虚拟化.

虚拟机 (virtual machine)上可以运行它自己的操作系统(也叫做Guest OS) 。

参考资料

声明:未经允许禁止转载 东东东 陈煜东的博客 文章,谢谢。如经授权,转载请注明: 转载自东东东 陈煜东的博客

本文链接地址: 域(Domains) 客户机(Guests) 虚拟机(Virtual Machines)区别 – https://www.chenyudong.com/archives/domains-guests-and-virtual-machines.html

分类: 虚拟化

查看virsh管理qemu虚拟机日志信息和libvirtd日志信息

在软件的开发和运行过程中,程序的运行日志log是不能少的。我们可以从log中发现程序的运行状态,以及可能出先的一些error.通常运行日志log上有时间、信息级别(level)、消息输出(message)。通过分析日志,我们可以从中获得程序的运行信息,方便我们的调试、恢复等.

在libvirt程序管理VM虚拟机时,也会有日志的记录.既有libvirtd的后台程序的日志,也有vm日志.接下来,我们设置一些日志的信息.

libvirtd的运行日志

在运行libvirtd的时候,我们需要获得lbivirtd的运行信息.所以我们需要找到他的日志文件.一般情况下,它是在/var/log/libvirt/libvirtd.log路径下.

可能在这个目录下没有发现这个的日志文件.那么就要配置一些libvitd的参数了.

编辑文件/etc/libvirt/libvirtd.conf

#将日志级别设置为 1(调试)
log_level = 1
#指定日志输出文件名称
log_outputs="1:file:/var/log/libvirt/libvirtd.log"
注意 :libvirtd. 日志文件可能会飞速增长。 用户应配置logrotate ,否则您的 /var 文件系统最后会装满内容。

以上的日志的输出级别为debug级别.这个级别的日志是最多的,一般只在开发以及测试的时候使用.而在生产运行环境中,日志的级别为info,warn,error,fatal. 以下前面的数字为他们的level.

  • 1 debug
  • 2 info
  • 3 warn
  • 4 error
  • 5 fatal

重启libvirtd 。虚拟机Guest操作系统正在运行时可重启 libvirtd。

# /etc/init.d/libvirtd restart

如果在目录下还是没发现日志文件,那么你可能需要使用一下命令来运行libvirtd.

libvirtd --daemon --listen --config /etc/libvirt/libvirtd.conf

查看virsh管理qemu虚拟机的信息

在使用virsh管理qemu的虚拟机时候,也是有日志的输出的.

具体的log在目录/var/log/livirt/qemu/ 下面,具体的log文件名与虚拟机名字关联.

声明:未经允许禁止转载 东东东 陈煜东的博客 文章,谢谢。如经授权,转载请注明: 转载自东东东 陈煜东的博客

本文链接地址: 查看virsh管理qemu虚拟机日志信息和libvirtd日志信息 – https://www.chenyudong.com/archives/qemu-vm-log-and-libvirtd-log.html

分类: 虚拟化

virsh使用qemu+tcp访问远程libvirtd

因为ssh的不能访问 所以使用tcp进行对远程libvirtd进行连接访问,例如

virsh -c qemu+tcp://example.com/system

修改文件vim /etc/sysconfig/libvirtd,用来启用tcp的端口

LIBVIRTD_CONFIG=/etc/libvirt/libvirtd.conf

LIBVIRTD_ARGS="--listen"

修改文件vim /etc/libvirt/libvirtd.conf

listen_tls = 0

listen_tcp = 1

tcp_port = "16509"

listen_addr = "0.0.0.0"

auth_tcp = "none"

运行 libvirtd

service libvirtd restart

如果没起效果(我的就没有生效 :( ),那么使用命令行:

libvirtd --daemon --listen --config /etc/libvirt/libvirtd.conf

查看运行进程

[root@ddd run]# ps aux | grep libvirtd
root 16563 1.5 0.1 925880 7056 ? Sl 16:01 0:28 libvirtd -d -l --config /etc/libvirt/libvirtd.conf

查看端口

[root@ddd run]# netstat -apn | grep tcp
tcp        0      0 0.0.0.0:16509           0.0.0.0:*               LISTEN      13971/libvirtd      

在source host连接dest host远程libvirtd查看信息

virsh -c qemu+tcp://211.87.***.97/system

Welcome to virsh, the virtualization interactive terminal.

Type: 'help' for help with commands
'quit' to quit

成功使用tcp去访问libvirtd。

声明:未经允许禁止转载 东东东 陈煜东的博客 文章,谢谢。如经授权,转载请注明: 转载自东东东 陈煜东的博客

本文链接地址: virsh使用qemu+tcp访问远程libvirtd – https://www.chenyudong.com/archives/libvirt-connect-to-libvirtd-with-tcp-qemu.html

分类: 虚拟化

使用libvirt和qemu将pci pass through设备添加到虚拟机上

透传的优势

guest使用透传设备可以获得设备近乎原生的性能,

PCI pass-throught设备给动态迁移带来的问题, dest host可能没有同样的硬件.

就算可以模拟一个设备,但是原始设备的内部状态不能获得.

VT-d support

In order to assign devices in KVM, you’ll need a system which supports VT-d. This has nothing to do with the VT-x support of your CPU, VT-d needs to be supported by both your chipset on your motherboard and by your CPU.

If you are in doubt whether your motherboard or CPU supports VT-d or not, the Xen VT-d wikipage has some pointers of VT-d enabled chipsets, motherboards and CPUs: http://wiki.xensource.com/xenwiki/VTdHowTo

If your hardware doesn’t have an IOMMU (“Intel VT-d” support in case of Intel – “AMD I/O Virtualization Technology” support in case of AMD), you’ll not be able to assign devices in KVM. Some work towards allowing this were done, but the code never made it into KVM, due to various issues with the code. At the moment it doesn’t seem like device assignment without hardware support, will ever be integrated into KVM.

Assignment of graphics cards are not officially supported at the moment, but there has been some success passing through a secondary Radeon HD 5850 as a VM’s secondary display.

资料:http://www.linux-kvm.org/page/How_to_assign_devices_with_VT-d_in_KVM

在host选择PCI pass through设备

reboot and verify that your system has IOMMU support

AMD Machine

dmesg | grep AMD-Vi
 ...
 AMD-Vi: Enabling IOMMU at 0000:00:00.2 cap 0x40
 AMD-Vi: Lazy IO/TLB flushing enabled
 AMD-Vi: Initialized for Passthrough Mode
 ...

Intel Machine

dmesg | grep -e DMAR -e IOMMU
...
DMAR:DRHD base: 0x000000feb03000 flags: 0x0
IOMMU feb03000: ver 1:0 cap c9008020e30260 ecap 1000
...

If you get no output you’ll need to fix this before moving on. Check if your hardware supports VT-d and check that it has been enabled in BIOS.

NOTE: If you still get an error “No IOMMU found.” Check dmesg for errors suggesting your BIOS is broken. Another possible reason: CONFIG_DMAR_DEFAULT_ON is not set. In that case, pass “intel_iommu=on” as kernel parameter to enable it. AMD uses different kernel parameter than Intel, on AMD you need to pass “iommu=pt iommu=1”.

请看附录:No IOMMU found 解决

选择要使用的透传设备

# lspci -nn
00:00.0 Host bridge [0600]: Intel Corporation 2nd Generation Core Processor Family DRAM Controller [8086:0100] (rev 09)
......
00:1b.0 Audio device [0403]: Intel Corporation 6 Series/C200 Series Chipset Family High Definition Audio Controller [8086:1c20] (rev 04)
.....
00:1f.3 SMBus [0c05]: Intel Corporation 6 Series/C200 Series Chipset Family SMBus Controller [8086:1c22] (rev 04)

友情提示:使用透传设备时,拿USB控制器作实验,可能鼠标键盘不能使用.请谨慎.

将设备从宿主机上解除绑定

使用echo命令,将设备从host机器上解除绑定,将来用于guest机器. For example:

echo "8086 1c20" > /sys/bus/pci/drivers/pci-stub/new_id
echo 0000:00:1b.0 > /sys/bus/pci/devices/0000:00:1b.0/driver/unbind
echo 0000:00:1b.0 > /sys/bus/pci/drivers/pci-stub/bind

关闭虚拟机

关闭虚拟机,修改配置文件.

使用libvirt进行pci pass through

修改虚拟机配置文件

<devices> …
    <hostdev mode='subsystem' type='pci' managed='yes'>
      <source>
         <address domain='0x000' bus='0x00′ slot='0x1b' function='0x0' />
      </source>
   </hostdev>
</devices>

在修改完虚拟机配置文件后,运行虚拟机.

使用qemu进行pci pass through

使用qemu进行pci pass through也是一样的简单的.我们需要一个已经创建好操作系统的虚拟机.

在qemu命令行运行以下命令以启动虚拟机

/usr/bin/qemu-kvm -name vdisk -enable-kvm -m 512 -smp 2 \
-hda /mnt/nfs/vdisk.img \
-monitor stdio \
-vnc 0.0.0.0:0 \
-device pci-assign,host=00:1b.0

这样就将设备挂载到虚拟机上了.

  • 参数-device pci-assign,host=00:1b.0说的是使用一个pci设备,并提供一个设备的地址.
  • 参数-monitor stdio是使用一个标准的控制台输出.在命令行中进行输入命令,等等迁移的时候也在这里输入命令.

附录1:No IOMMU found 解决

启动虚拟机的时候出现了iommu的问题.以供大家参考

1.查看错误日志说明

在配置好XML文件后,启动虚拟机,遇到一个问题.

error: Failed to start domain vdisk
error: Unable to read from monitor: Connection reset by peer

查看虚拟机日志( cat /var/log/libvirt/qemu/vdisk.log )信息.

char device redirected to /dev/pts/3
No IOMMU found. Unable to assign device "hostdev0"
qemu-system-x86_64: -device pci-assign,configfd=20,host=00:1b.0,id=hostdev0,bus=pci.0,addr=0x4: Device 'pci-assign' could not be initialized
2013-07-08 06:41:23.256+0000: shutting down

上网查阅资料,说是要在BIOS上设置虚拟化,然后在引导程序里也要设置iommu.可以查看一下自己的电脑信息是否开启了.

2.查看信息gurb的引导信息

# cat /proc/cmdline
BOOT_IMAGE=/vmlinuz-3.9.6-200.fc18.x86_64 root=/dev/mapper/fedora-home ro rd.lvm.lv=fedora/swap rd.md=0 rd.dm=0 rd.lvm.lv=fedora/home rd.luks=0 vconsole.keymap=us rhgb quiet LANG=en_US.UTF-8

可以发现,我的还未开启intel_iommu=on选项.所以接下来我们来激活它.

3.激活intel_iommu=on

Activate Intel VT-d in the kernel

Activate Intel VT-d in the kernel by appending the intel_iommu=on parameter to the kernel line of the kernel line in the/boot/grub/grub.conf file. The example below is a modified grub.conf file with Intel VT-d activated.

对于intel的cpu和amd的cpu,在grub配置上是不同的,具体的配置请参考文章:http://pve.proxmox.com/wiki/Pci_passthrough

4.更新grub

在编辑完grub文件后,需要更新

grub2-mkconfig   # fedora arch centos
update-grub            # ubuntu debian

5.重启电脑,使其生效

# cat /proc/cmdline
BOOT_IMAGE=/vmlinuz-3.9.6-200.fc18.x86_64 root=/dev/mapper/fedora-home ro rd.lvm.lv=fedora/swap rd.md=0 rd.dm=0 rd.lvm.lv=fedora/home rd.luks=0 vconsole.keymap=us rhgb quiet intel_iommu=on LANG=en_US.UTF-8

发现开机已经启动了inte _iommu=on了.再次启动虚拟机已经就不会出现这个bug了.

附录2 PCI pass through 失败要关闭SELinux

我用的是Fedora 18 ,将SELinux给disalbed了,但是发现PCI pass through出先问题.上网看到文章PCI passthrough fails in qemu-kvm unless selinux is disabled 说,要将selinux设置成permissive模式,于是这个问题解决了.

参考资料

声明:未经允许禁止转载 东东东 陈煜东的博客 文章,谢谢。如经授权,转载请注明: 转载自东东东 陈煜东的博客

本文链接地址: 使用libvirt和qemu将pci pass through设备添加到虚拟机上 – https://www.chenyudong.com/archives/add-pci-pass-through-device-to-guest-vm-with-libvirt-and-qemu.html

分类: 虚拟化

较早的文章

Copyright © 2017 东东东 陈煜东的博客 粤ICP备13059639号-1

SITEMAP回到顶部 ↑