设为首页 收藏本站
查看: 2118|回复: 0

[经验分享] Xen授权表的使用

[复制链接]

尚未签到

发表于 2015-4-13 10:42:28 | 显示全部楼层 |阅读模式
  完全照搬原文,原文地址:http://fire-flying.diandian.com/。
  ///////////////////////////////////////////////////////////////////////////////////////////////////////////////
  原文的代码可能比较旧,在我的机器上已经不能运行,下面是经我修改过的,先看domU端的代码:


DSC0000.gif DSC0001.gif


#include
#include
#include
#include
#include
#include
#include
#include
#include
//#include
#include
#include
#include
#include
unsigned long page;
struct as_request {
unsigned int id;
unsigned int status;
unsigned int operation;
};
struct as_response {
unsigned int id;
unsigned int status;
unsigned int operation;
};
DEFINE_RING_TYPES(as, struct as_request, struct as_response);
struct info_t {
struct as_front_ring ring;
grant_ref_t gref;
int irq;
int port;
}info;
#define DOM0_ID 0
static struct proc_dir_entry *proc_dir = NULL;
static struct proc_dir_entry *proc_file = NULL;
char proc_data[20];
int send_request_to_dom0(void)
{
struct as_request *ring_req;
int notify;
static int reqid = 9;
ring_req = RING_GET_REQUEST(&(info.ring), info.ring.req_prod_pvt);
ring_req->id = reqid;
ring_req->operation = reqid;
ring_req->status = reqid;
printk(KERN_DEBUG "\nxen:DomU: Fill in IDX-%d, with id=%d, op=%d, st=%d",
info.ring.req_prod_pvt, ring_req->id, ring_req->operation, ring_req->status);
reqid++;
info.ring.req_prod_pvt += 1;
RING_PUSH_REQUESTS_AND_CHECK_NOTIFY(&(info.ring), notify);
if (notify) {
printk(KERN_DEBUG "\nxen: DomU: sent a req to Dom0");
notify_remote_via_irq(info.irq);
} else {
printk(KERN_DEBUG "\nxen:DomU: No notify req to Dom0");
notify_remote_via_irq(info.irq);
}
printk("...\n");
return 0;
}
int file_write (struct file *filp, const char __user *buff, unsigned long len, void *data)
{
int value;
printk(KERN_DEBUG "\nxen:domU: file_write %lu bytes", len);
if (copy_from_user(&proc_data[0], buff, len))
return -EFAULT;
proc_data[len] = '\x0';
value = simple_strtol(proc_data, 0, 10);
switch(value) {
case 1:
send_request_to_dom0();
printk(KERN_DEBUG " ,value = %d", value);
break;
default:
printk(KERN_DEBUG " ,value not recongnized!");
}
return len;
}
int file_read(char *page, char **start, off_t off, int count, int *eof, void *data)
{
sprintf(page, "%s", proc_data);
return strlen(page);
}
int create_procfs_entry(void)
{
int ret = 0;
proc_dir = proc_mkdir("demo", NULL);
if (!proc_dir) {
printk(KERN_DEBUG "\nxen:domU could not create demo entry in procfs");
ret = - EAGAIN;
return ret;
}
proc_file = create_proc_entry("file", 0600, proc_dir);
if (proc_file) {
proc_file->read_proc = file_read;
proc_file->write_proc = file_write;
//proc_file->owner = THIS_MODULE;
} else {
printk(KERN_DEBUG "\nxen:domU Could not create /proc/demo/file");
ret = -EAGAIN;
return ret;
}
return ret;
}
static irqreturn_t as_int (int irq, void *dev_id)
{
struct as_response *ring_resp;
RING_IDX i, rp;
printk("\nxen:DomU: as_int called");
again:
rp = info.ring.sring->rsp_prod;
printk(KERN_DEBUG "\nxen:DomU:ring pointers %d to %d", info.ring.rsp_cons, rp);
for (i = info.ring.rsp_cons; i != rp; i++) {
unsigned long id;
ring_resp = RING_GET_RESPONSE(&(info.ring), i);
printk(KERN_DEBUG "\nxen:domU: Recvd in IDX-%d, with id=%d, op=%d, st=%d", i, ring_resp->id, ring_resp->operation, ring_resp->status);
id = ring_resp->id;
switch(ring_resp->operation) {
case 0:
printk(KERN_DEBUG "\nxen:DomU: operation: 0");
break;
default:
break;
}
}
info.ring.rsp_cons = i;
if (i != info.ring.req_prod_pvt) {
int more_to_do;
RING_FINAL_CHECK_FOR_RESPONSES(&info.ring, more_to_do);
if (more_to_do)
goto again;
} else
info.ring.sring->rsp_event = i + 1;
return IRQ_HANDLED;
}
int gnt_init(void)
{
int mfn;
int err;
//int i;
struct as_sring *sring;
//char *p;
////////////
struct evtchn_alloc_unbound alloc_unbound;
printk(KERN_INFO "gnt_init\n");
page =  __get_free_pages(GFP_KERNEL, 0);
if (page == 0) {
printk(KERN_DEBUG "\nxen:DomU:could not get free page");
return 0;
}
sring = (struct as_sring *)page;
SHARED_RING_INIT(sring);
FRONT_RING_INIT(&(info.ring), sring, PAGE_SIZE);
mfn = virt_to_mfn(page);
/*
p = (char *)page + PAGE_SIZE - 1;
for (i = 0; i addr, GNTMAP_host_map, info.gref, info.remoteDomain);//为下面的hypercall的参数做准备
if (HYPERVISOR_grant_table_op(GNTTABOP_map_grant_ref, &ops, 1)) {//页面映射
printk(KERN_DEBUG "\nxen:dom0: HYPERVISOR map grant ref failed");
return -EFAULT;
}
if (ops.status) {
printk(KERN_DEBUG "\nxen: dom0: HYPERVISOR map grant ref failed status = %d", ops.status);
return -EFAULT;
}
printk(KERN_DEBUG "\nxen:dom0:shared_page=%x, handle = %x, status = %x", (unsigned int)v_start->addr, ops.handle, ops.status);
unmap_ops.host_addr = (unsigned long)(v_start->addr);
unmap_ops.handle = ops.handle;
//////////////
/*
p = (char *)(v_start->addr) + PAGE_SIZE - 1;
printk(KERN_DEBUG "\nbytes in page");
for (i = 0;i addr;
BACK_RING_INIT(&info.ring, sring, PAGE_SIZE);
err = bind_interdomain_evtchn_to_irqhandler(info.remoteDomain, info.evtchn, as_int, 0, "dom0-backend", &info);
if (err < 0) {
printk(KERN_DEBUG "\nxen:dom0: gnt_init failed binding to evtchn");
err = HYPERVISOR_grant_table_op(GNTTABOP_unmap_grant_ref, &unmap_ops, 1);
return -EFAULT;
}
info.irq = err;
printk(KERN_DEBUG "\nxen:dom0:end gnt_int: int = %d", info.irq);
return 0;
}
static void gnt_exit(void)
{
int ret;
printk(KERN_DEBUG "\nxen:dom0:gnt_exit");
ret = HYPERVISOR_grant_table_op(GNTTABOP_unmap_grant_ref, &unmap_ops, 1);
if (ret == 0) {
printk(KERN_DEBUG "gnt_exit: unmapped shared frame");
} else {
printk(KERN_DEBUG "gnt_exit: unmapped shared frame failed");
}
printk("...\n");
}
module_init(gnt_init);
module_exit(gnt_exit);
MODULE_LICENSE("GPL");
Domain0
  dom0所做的工作:
  1. 因为我们需要将domU的一部分内存映射到dom0内,因此调用alloc_vm_area预留一段内核空间和页表,但是实际并没有映射;
  2. 调用gnttab_set_map_op为超级调用的参数做准备,然后调用HYPERVISOR_grant_table_op(GTNTABOP_map_grant_ref, ...)进行页面映射;
  3. 调用BACK_RING_INIT初始化共享环后端;
  4. 调用bind_interdomain_evtchn_to_irqhandler将端口与中断处理程序绑定,这样会得到中断号,注意端口号是模块函数的参数。

运维网声明 1、欢迎大家加入本站运维交流群:群②:261659950 群⑤:202807635 群⑦870801961 群⑧679858003
2、本站所有主题由该帖子作者发表,该帖子作者与运维网享有帖子相关版权
3、所有作品的著作权均归原作者享有,请您和我们一样尊重他人的著作权等合法权益。如果您对作品感到满意,请购买正版
4、禁止制作、复制、发布和传播具有反动、淫秽、色情、暴力、凶杀等内容的信息,一经发现立即删除。若您因此触犯法律,一切后果自负,我们对此不承担任何责任
5、所有资源均系网友上传或者通过网络收集,我们仅提供一个展示、介绍、观摩学习的平台,我们不对其内容的准确性、可靠性、正当性、安全性、合法性等负责,亦不承担任何法律责任
6、所有作品仅供您个人学习、研究或欣赏,不得用于商业或者其他用途,否则,一切后果均由您自己承担,我们对此不承担任何法律责任
7、如涉及侵犯版权等问题,请您及时通知我们,我们将立即采取措施予以解决
8、联系人Email:admin@iyunv.com 网址:www.yunweiku.com

所有资源均系网友上传或者通过网络收集,我们仅提供一个展示、介绍、观摩学习的平台,我们不对其承担任何法律责任,如涉及侵犯版权等问题,请您及时通知我们,我们将立即处理,联系人Email:kefu@iyunv.com,QQ:1061981298 本贴地址:https://www.yunweiku.com/thread-56595-1-1.html 上篇帖子: Xen入门系列四【Xen 管理实操】 下篇帖子: xen虚拟化及工作原理
您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

扫码加入运维网微信交流群X

扫码加入运维网微信交流群

扫描二维码加入运维网微信交流群,最新一手资源尽在官方微信交流群!快快加入我们吧...

扫描微信二维码查看详情

客服E-mail:kefu@iyunv.com 客服QQ:1061981298


QQ群⑦:运维网交流群⑦ QQ群⑧:运维网交流群⑧ k8s群:运维网kubernetes交流群


提醒:禁止发布任何违反国家法律、法规的言论与图片等内容;本站内容均来自个人观点与网络等信息,非本站认同之观点.


本站大部分资源是网友从网上搜集分享而来,其版权均归原作者及其网站所有,我们尊重他人的合法权益,如有内容侵犯您的合法权益,请及时与我们联系进行核实删除!



合作伙伴: 青云cloud

快速回复 返回顶部 返回列表