From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1753213AbdLSTvP (ORCPT ); Tue, 19 Dec 2017 14:51:15 -0500 Received: from mga01.intel.com ([192.55.52.88]:17636 "EHLO mga01.intel.com" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1752833AbdLSTga (ORCPT ); Tue, 19 Dec 2017 14:36:30 -0500 X-Amp-Result: SKIPPED(no attachment in message) X-Amp-File-Uploaded: False X-ExtLoop1: 1 X-IronPort-AV: E=Sophos;i="5.45,428,1508828400"; d="scan'208";a="4018491" From: Dongwon Kim To: linux-kernel@vger.kernel.org Cc: dri-devel@lists.freedesktop.org, xen-devel@lists.xenproject.org, mateuszx.potrola@intel.com, dongwon.kim@intel.com Subject: [RFC PATCH 07/60] hyper_dmabuf: message parsing done via workqueue Date: Tue, 19 Dec 2017 11:29:23 -0800 Message-Id: <1513711816-2618-7-git-send-email-dongwon.kim@intel.com> X-Mailer: git-send-email 2.7.4 In-Reply-To: <1513711816-2618-1-git-send-email-dongwon.kim@intel.com> References: <1513711816-2618-1-git-send-email-dongwon.kim@intel.com> MIME-Version: 1.0 Content-Type: text/plain; charset="utf-8" Content-Transfer-Encoding: 8bit Sender: linux-kernel-owner@vger.kernel.org List-ID: X-Mailing-List: linux-kernel@vger.kernel.org Use workqueue mechanism to delay message parsing done after exiting from ISR to reduce ISR execution time. Signed-off-by: Dongwon Kim --- drivers/xen/hyper_dmabuf/hyper_dmabuf_drv.c | 13 ++ drivers/xen/hyper_dmabuf/hyper_dmabuf_drv.h | 5 + drivers/xen/hyper_dmabuf/hyper_dmabuf_ioctl.c | 4 +- drivers/xen/hyper_dmabuf/hyper_dmabuf_msg.c | 155 ++++++++++++++------- .../xen/hyper_dmabuf/xen/hyper_dmabuf_xen_comm.c | 75 ++++------ .../xen/hyper_dmabuf/xen/hyper_dmabuf_xen_comm.h | 7 - 6 files changed, 152 insertions(+), 107 deletions(-) diff --git a/drivers/xen/hyper_dmabuf/hyper_dmabuf_drv.c b/drivers/xen/hyper_dmabuf/hyper_dmabuf_drv.c index 0698327..70b4878 100644 --- a/drivers/xen/hyper_dmabuf/hyper_dmabuf_drv.c +++ b/drivers/xen/hyper_dmabuf/hyper_dmabuf_drv.c @@ -1,5 +1,8 @@ #include /* module_init, module_exit */ #include /* version info, MODULE_LICENSE, MODULE_AUTHOR, printk() */ +#include +#include +#include "hyper_dmabuf_drv.h" #include "hyper_dmabuf_conf.h" #include "hyper_dmabuf_list.h" #include "xen/hyper_dmabuf_xen_comm_list.h" @@ -10,6 +13,8 @@ MODULE_AUTHOR("IOTG-PED, INTEL"); int register_device(void); int unregister_device(void); +struct hyper_dmabuf_private hyper_dmabuf_private; + /*===============================================================================================*/ static int hyper_dmabuf_drv_init(void) { @@ -24,6 +29,10 @@ static int hyper_dmabuf_drv_init(void) printk( KERN_NOTICE "initializing database for imported/exported dmabufs\n"); + /* device structure initialization */ + /* currently only does work-queue initialization */ + hyper_dmabuf_private.work_queue = create_workqueue("hyper_dmabuf_wqueue"); + ret = hyper_dmabuf_table_init(); if (ret < 0) { return -EINVAL; @@ -45,6 +54,10 @@ static void hyper_dmabuf_drv_exit(void) hyper_dmabuf_table_destroy(); hyper_dmabuf_ring_table_init(); + /* destroy workqueue */ + if (hyper_dmabuf_private.work_queue) + destroy_workqueue(hyper_dmabuf_private.work_queue); + printk( KERN_NOTICE "dma_buf-src_sink model: Exiting" ); unregister_device(); } diff --git a/drivers/xen/hyper_dmabuf/hyper_dmabuf_drv.h b/drivers/xen/hyper_dmabuf/hyper_dmabuf_drv.h index 2dad9a6..6145d29 100644 --- a/drivers/xen/hyper_dmabuf/hyper_dmabuf_drv.h +++ b/drivers/xen/hyper_dmabuf/hyper_dmabuf_drv.h @@ -1,6 +1,11 @@ #ifndef __LINUX_PUBLIC_HYPER_DMABUF_DRV_H__ #define __LINUX_PUBLIC_HYPER_DMABUF_DRV_H__ +struct hyper_dmabuf_private { + struct device *device; + struct workqueue_struct *work_queue; +}; + typedef int (*hyper_dmabuf_ioctl_t)(void *data); struct hyper_dmabuf_ioctl_desc { diff --git a/drivers/xen/hyper_dmabuf/hyper_dmabuf_ioctl.c b/drivers/xen/hyper_dmabuf/hyper_dmabuf_ioctl.c index af94359..e4d8316 100644 --- a/drivers/xen/hyper_dmabuf/hyper_dmabuf_ioctl.c +++ b/drivers/xen/hyper_dmabuf/hyper_dmabuf_ioctl.c @@ -15,9 +15,7 @@ #include "xen/hyper_dmabuf_xen_comm_list.h" #include "hyper_dmabuf_msg.h" -struct hyper_dmabuf_private { - struct device *device; -} hyper_dmabuf_private; +extern struct hyper_dmabuf_private hyper_dmabuf_private; static uint32_t hyper_dmabuf_id_gen(void) { /* TODO: add proper implementation */ diff --git a/drivers/xen/hyper_dmabuf/hyper_dmabuf_msg.c b/drivers/xen/hyper_dmabuf/hyper_dmabuf_msg.c index 3237e50..0166e61 100644 --- a/drivers/xen/hyper_dmabuf/hyper_dmabuf_msg.c +++ b/drivers/xen/hyper_dmabuf/hyper_dmabuf_msg.c @@ -3,12 +3,23 @@ #include #include #include +#include +#include +#include "hyper_dmabuf_drv.h" #include "hyper_dmabuf_imp.h" //#include "hyper_dmabuf_remote_sync.h" #include "xen/hyper_dmabuf_xen_comm.h" #include "hyper_dmabuf_msg.h" #include "hyper_dmabuf_list.h" +extern struct hyper_dmabuf_private hyper_dmabuf_private; + +struct cmd_process { + struct work_struct work; + struct hyper_dmabuf_ring_rq *rq; + int domid; +}; + void hyper_dmabuf_create_request(struct hyper_dmabuf_ring_rq *request, enum hyper_dmabuf_command command, int *operands) { @@ -71,18 +82,17 @@ void hyper_dmabuf_create_request(struct hyper_dmabuf_ring_rq *request, } } -int hyper_dmabuf_msg_parse(int domid, struct hyper_dmabuf_ring_rq *req) +void cmd_process_work(struct work_struct *work) { - uint32_t i, ret; struct hyper_dmabuf_imported_sgt_info *imported_sgt_info; - struct hyper_dmabuf_sgt_info *sgt_info; - - /* make sure req is not NULL (may not be needed) */ - if (!req) { - return -EINVAL; - } + struct hyper_dmabuf_sgt_info *sgt_info; + struct cmd_process *proc = container_of(work, struct cmd_process, work); + struct hyper_dmabuf_ring_rq *req; + int domid; + int i; - req->status = HYPER_DMABUF_REQ_PROCESSED; + req = proc->rq; + domid = proc->domid; switch (req->command) { case HYPER_DMABUF_EXPORT: @@ -115,33 +125,6 @@ int hyper_dmabuf_msg_parse(int domid, struct hyper_dmabuf_ring_rq *req) hyper_dmabuf_register_imported(imported_sgt_info); break; - case HYPER_DMABUF_DESTROY: - /* destroy sg_list for hyper_dmabuf_id on remote side */ - /* command : DMABUF_DESTROY, - * operands0 : hyper_dmabuf_id - */ - - imported_sgt_info = - hyper_dmabuf_find_imported(req->operands[0]); - - if (imported_sgt_info) { - hyper_dmabuf_cleanup_imported_pages(imported_sgt_info); - - hyper_dmabuf_remove_imported(req->operands[0]); - - /* TODO: cleanup sgt on importer side etc */ - } - - /* Notify exporter that buffer is freed and it can cleanup it */ - req->status = HYPER_DMABUF_REQ_NEEDS_FOLLOW_UP; - req->command = HYPER_DMABUF_DESTROY_FINISH; - -#if 0 /* function is not implemented yet */ - - ret = hyper_dmabuf_destroy_sgt(req->hyper_dmabuf_id); -#endif - break; - case HYPER_DMABUF_DESTROY_FINISH: /* destroy sg_list for hyper_dmabuf_id on local side */ /* command : DMABUF_DESTROY_FINISH, @@ -180,33 +163,101 @@ int hyper_dmabuf_msg_parse(int domid, struct hyper_dmabuf_ring_rq *req) */ break; - /* requesting the other side to setup another ring channel for reverse direction */ - case HYPER_DMABUF_EXPORTER_RING_SETUP: - /* command: HYPER_DMABUF_EXPORTER_RING_SETUP - * no operands needed */ + case HYPER_DMABUF_IMPORTER_RING_SETUP: + /* command: HYPER_DMABUF_IMPORTER_RING_SETUP */ + /* no operands needed */ + hyper_dmabuf_importer_ringbuf_init(domid, req->operands[0], req->operands[1]); + + break; + + default: + /* shouldn't get here */ + /* no matched command, nothing to do.. just return error */ + break; + } + + kfree(req); + kfree(proc); +} + +int hyper_dmabuf_msg_parse(int domid, struct hyper_dmabuf_ring_rq *req) +{ + struct cmd_process *proc; + struct hyper_dmabuf_ring_rq *temp_req; + struct hyper_dmabuf_imported_sgt_info *imported_sgt_info; + int ret; + + if (!req) { + printk("request is NULL\n"); + return -EINVAL; + } + + if ((req->command < HYPER_DMABUF_EXPORT) || + (req->command > HYPER_DMABUF_IMPORTER_RING_SETUP)) { + printk("invalid command\n"); + return -EINVAL; + } + + req->status = HYPER_DMABUF_REQ_PROCESSED; + + /* HYPER_DMABUF_EXPORTER_RING_SETUP requires immediate + * follow up so can't be processed in workqueue + */ + if (req->command == HYPER_DMABUF_EXPORTER_RING_SETUP) { ret = hyper_dmabuf_exporter_ringbuf_init(domid, &req->operands[0], &req->operands[1]); if (ret < 0) { req->status = HYPER_DMABUF_REQ_ERROR; - return -EINVAL; } req->status = HYPER_DMABUF_REQ_NEEDS_FOLLOW_UP; req->command = HYPER_DMABUF_IMPORTER_RING_SETUP; - break; - case HYPER_DMABUF_IMPORTER_RING_SETUP: - /* command: HYPER_DMABUF_IMPORTER_RING_SETUP */ - /* no operands needed */ - ret = hyper_dmabuf_importer_ringbuf_init(domid, req->operands[0], req->operands[1]); - if (ret < 0) - return -EINVAL; + return req->command; + } - break; + /* HYPER_DMABUF_DESTROY requires immediate + * follow up so can't be processed in workqueue + */ + if (req->command == HYPER_DMABUF_DESTROY) { + /* destroy sg_list for hyper_dmabuf_id on remote side */ + /* command : DMABUF_DESTROY, + * operands0 : hyper_dmabuf_id + */ + imported_sgt_info = + hyper_dmabuf_find_imported(req->operands[0]); - default: - /* no matched command, nothing to do.. just return error */ - return -EINVAL; + if (imported_sgt_info) { + hyper_dmabuf_cleanup_imported_pages(imported_sgt_info); + + hyper_dmabuf_remove_imported(req->operands[0]); + + /* TODO: cleanup sgt on importer side etc */ + } + + /* Notify exporter that buffer is freed and it can cleanup it */ + req->status = HYPER_DMABUF_REQ_NEEDS_FOLLOW_UP; + req->command = HYPER_DMABUF_DESTROY_FINISH; + +#if 0 /* function is not implemented yet */ + + ret = hyper_dmabuf_destroy_sgt(req->hyper_dmabuf_id); +#endif + return req->command; } + temp_req = (struct hyper_dmabuf_ring_rq *)kmalloc(sizeof(*temp_req), GFP_KERNEL); + + memcpy(temp_req, req, sizeof(*temp_req)); + + proc = (struct cmd_process *) kcalloc(1, sizeof(struct cmd_process), + GFP_KERNEL); + + proc->rq = temp_req; + proc->domid = domid; + + INIT_WORK(&(proc->work), cmd_process_work); + + queue_work(hyper_dmabuf_private.work_queue, &(proc->work)); + return req->command; } diff --git a/drivers/xen/hyper_dmabuf/xen/hyper_dmabuf_xen_comm.c b/drivers/xen/hyper_dmabuf/xen/hyper_dmabuf_xen_comm.c index 22f2ef0..05855ba1 100644 --- a/drivers/xen/hyper_dmabuf/xen/hyper_dmabuf_xen_comm.c +++ b/drivers/xen/hyper_dmabuf/xen/hyper_dmabuf_xen_comm.c @@ -14,7 +14,6 @@ #include "../hyper_dmabuf_msg.h" static int export_req_id = 0; -static int import_req_id = 0; int32_t hyper_dmabuf_get_domid(void) { @@ -37,12 +36,6 @@ int hyper_dmabuf_next_req_id_export(void) return export_req_id; } -int hyper_dmabuf_next_req_id_import(void) -{ - import_req_id++; - return import_req_id; -} - /* For now cache latast rings as global variables TODO: keep them in list*/ static irqreturn_t hyper_dmabuf_front_ring_isr(int irq, void *dev_id); static irqreturn_t hyper_dmabuf_back_ring_isr(int irq, void *dev_id); @@ -81,7 +74,8 @@ int hyper_dmabuf_exporter_ringbuf_init(int rdomain, grant_ref_t *refid, int *por alloc_unbound.dom = DOMID_SELF; alloc_unbound.remote_dom = rdomain; - ret = HYPERVISOR_event_channel_op(EVTCHNOP_alloc_unbound, &alloc_unbound); + ret = HYPERVISOR_event_channel_op(EVTCHNOP_alloc_unbound, + &alloc_unbound); if (ret != 0) { printk("Cannot allocate event channel\n"); return -EINVAL; @@ -96,7 +90,8 @@ int hyper_dmabuf_exporter_ringbuf_init(int rdomain, grant_ref_t *refid, int *por printk("Failed to setup event channel\n"); close.port = alloc_unbound.port; HYPERVISOR_event_channel_op(EVTCHNOP_close, &close); - gnttab_end_foreign_access(ring_info->gref_ring, 0, virt_to_mfn(shared_ring)); + gnttab_end_foreign_access(ring_info->gref_ring, 0, + virt_to_mfn(shared_ring)); return -EINVAL; } @@ -108,7 +103,8 @@ int hyper_dmabuf_exporter_ringbuf_init(int rdomain, grant_ref_t *refid, int *por *refid = ring_info->gref_ring; *port = ring_info->port; - printk("%s: allocated eventchannel gref %d port: %d irq: %d\n", __func__, + printk("%s: allocated eventchannel gref %d port: %d irq: %d\n", + __func__, ring_info->gref_ring, ring_info->port, ring_info->irq); @@ -162,8 +158,9 @@ int hyper_dmabuf_importer_ringbuf_init(int sdomain, grant_ref_t gref, int port) BACK_RING_INIT(&ring_info->ring_back, sring, PAGE_SIZE); - ret = bind_interdomain_evtchn_to_irqhandler(sdomain, port, hyper_dmabuf_back_ring_isr, 0, - NULL, (void*)ring_info); + ret = bind_interdomain_evtchn_to_irqhandler(sdomain, port, + hyper_dmabuf_back_ring_isr, 0, + NULL, (void*)ring_info); if (ret < 0) { return -EINVAL; } @@ -216,26 +213,20 @@ int hyper_dmabuf_send_request(int domain, struct hyper_dmabuf_ring_rq *req) return 0; } -/* called by interrupt (WORKQUEUE) */ -int hyper_dmabuf_send_response(struct hyper_dmabuf_ring_rp* response, int domain) -{ - /* as a importer and as a exporter */ - return 0; -} - /* ISR for request from exporter (as an importer) */ -static irqreturn_t hyper_dmabuf_back_ring_isr(int irq, void *dev_id) +static irqreturn_t hyper_dmabuf_back_ring_isr(int irq, void *info) { RING_IDX rc, rp; - struct hyper_dmabuf_ring_rq request; - struct hyper_dmabuf_ring_rp response; + struct hyper_dmabuf_ring_rq req; + struct hyper_dmabuf_ring_rp resp; + int notify, more_to_do; int ret; -// struct hyper_dmabuf_work *work; - struct hyper_dmabuf_ring_info_import *ring_info = (struct hyper_dmabuf_ring_info_import *)dev_id; + struct hyper_dmabuf_ring_info_import *ring_info; struct hyper_dmabuf_back_ring *ring; + ring_info = (struct hyper_dmabuf_ring_info_import *)info; ring = &ring_info->ring_back; do { @@ -246,22 +237,16 @@ static irqreturn_t hyper_dmabuf_back_ring_isr(int irq, void *dev_id) if (RING_REQUEST_CONS_OVERFLOW(ring, rc)) break; - memcpy(&request, RING_GET_REQUEST(ring, rc), sizeof(request)); + memcpy(&req, RING_GET_REQUEST(ring, rc), sizeof(req)); printk("Got request\n"); ring->req_cons = ++rc; - /* TODO: probably using linked list for multiple requests then let - * a task in a workqueue to process those is better idea becuase - * we do not want to stay in ISR for long. - */ - ret = hyper_dmabuf_msg_parse(ring_info->sdomain, &request); + ret = hyper_dmabuf_msg_parse(ring_info->sdomain, &req); if (ret > 0) { - /* build response */ - memcpy(&response, &request, sizeof(response)); - - /* we sent back modified request as a response.. we might just need to have request only..*/ - memcpy(RING_GET_RESPONSE(ring, ring->rsp_prod_pvt), &response, sizeof(response)); + memcpy(&resp, &req, sizeof(resp)); + memcpy(RING_GET_RESPONSE(ring, ring->rsp_prod_pvt), &resp, + sizeof(resp)); ring->rsp_prod_pvt++; RING_PUSH_RESPONSES_AND_CHECK_NOTIFY(ring, notify); @@ -281,15 +266,17 @@ static irqreturn_t hyper_dmabuf_back_ring_isr(int irq, void *dev_id) } /* ISR for responses from importer */ -static irqreturn_t hyper_dmabuf_front_ring_isr(int irq, void *dev_id) +static irqreturn_t hyper_dmabuf_front_ring_isr(int irq, void *info) { /* front ring only care about response from back */ - struct hyper_dmabuf_ring_rp *response; + struct hyper_dmabuf_ring_rp *resp; RING_IDX i, rp; int more_to_do, ret; - struct hyper_dmabuf_ring_info_export *ring_info = (struct hyper_dmabuf_ring_info_export *)dev_id; + struct hyper_dmabuf_ring_info_export *ring_info; struct hyper_dmabuf_front_ring *ring; + + ring_info = (struct hyper_dmabuf_ring_info_export *)info; ring = &ring_info->ring_front; do { @@ -298,20 +285,18 @@ static irqreturn_t hyper_dmabuf_front_ring_isr(int irq, void *dev_id) for (i = ring->rsp_cons; i != rp; i++) { unsigned long id; - response = RING_GET_RESPONSE(ring, i); - id = response->response_id; + resp = RING_GET_RESPONSE(ring, i); + id = resp->response_id; - if (response->status == HYPER_DMABUF_REQ_NEEDS_FOLLOW_UP) { + if (resp->status == HYPER_DMABUF_REQ_NEEDS_FOLLOW_UP) { /* parsing response */ - ret = hyper_dmabuf_msg_parse(ring_info->rdomain, (struct hyper_dmabuf_ring_rq*)response); + ret = hyper_dmabuf_msg_parse(ring_info->rdomain, + (struct hyper_dmabuf_ring_rq *)resp); if (ret < 0) { printk("getting error while parsing response\n"); } - } else if (response->status == HYPER_DMABUF_REQ_ERROR) { - printk("remote domain %d couldn't process request %d\n", ring_info->rdomain, response->command); } - } ring->rsp_cons = i; diff --git a/drivers/xen/hyper_dmabuf/xen/hyper_dmabuf_xen_comm.h b/drivers/xen/hyper_dmabuf/xen/hyper_dmabuf_xen_comm.h index 2754917..4ad0529 100644 --- a/drivers/xen/hyper_dmabuf/xen/hyper_dmabuf_xen_comm.h +++ b/drivers/xen/hyper_dmabuf/xen/hyper_dmabuf_xen_comm.h @@ -36,17 +36,10 @@ struct hyper_dmabuf_ring_info_import { struct hyper_dmabuf_back_ring ring_back; }; -//struct hyper_dmabuf_work { -// hyper_dmabuf_ring_rq requrest; -// struct work_struct msg_parse; -//}; - int32_t hyper_dmabuf_get_domid(void); int hyper_dmabuf_next_req_id_export(void); -int hyper_dmabuf_next_req_id_import(void); - /* exporter needs to generated info for page sharing */ int hyper_dmabuf_exporter_ringbuf_init(int rdomain, grant_ref_t *gref, int *port); -- 2.7.4 From mboxrd@z Thu Jan 1 00:00:00 1970 From: Dongwon Kim Subject: [RFC PATCH 07/60] hyper_dmabuf: message parsing done via workqueue Date: Tue, 19 Dec 2017 11:29:23 -0800 Message-ID: <1513711816-2618-7-git-send-email-dongwon.kim@intel.com> References: <1513711816-2618-1-git-send-email-dongwon.kim@intel.com> Mime-Version: 1.0 Content-Type: text/plain; charset="utf-8" Content-Transfer-Encoding: base64 Return-path: Received: from mga01.intel.com (mga01.intel.com [192.55.52.88]) by gabe.freedesktop.org (Postfix) with ESMTPS id 505966E334 for ; Tue, 19 Dec 2017 19:36:29 +0000 (UTC) In-Reply-To: <1513711816-2618-1-git-send-email-dongwon.kim@intel.com> List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: dri-devel-bounces@lists.freedesktop.org Sender: "dri-devel" To: linux-kernel@vger.kernel.org Cc: xen-devel@lists.xenproject.org, mateuszx.potrola@intel.com, dri-devel@lists.freedesktop.org, dongwon.kim@intel.com List-Id: dri-devel@lists.freedesktop.org VXNlIHdvcmtxdWV1ZSBtZWNoYW5pc20gdG8gZGVsYXkgbWVzc2FnZSBwYXJzaW5nIGRvbmUKYWZ0 ZXIgZXhpdGluZyBmcm9tIElTUiB0byByZWR1Y2UgSVNSIGV4ZWN1dGlvbiB0aW1lLgoKU2lnbmVk LW9mZi1ieTogRG9uZ3dvbiBLaW0gPGRvbmd3b24ua2ltQGludGVsLmNvbT4KLS0tCiBkcml2ZXJz L3hlbi9oeXBlcl9kbWFidWYvaHlwZXJfZG1hYnVmX2Rydi5jICAgICAgICB8ICAxMyArKwogZHJp dmVycy94ZW4vaHlwZXJfZG1hYnVmL2h5cGVyX2RtYWJ1Zl9kcnYuaCAgICAgICAgfCAgIDUgKwog ZHJpdmVycy94ZW4vaHlwZXJfZG1hYnVmL2h5cGVyX2RtYWJ1Zl9pb2N0bC5jICAgICAgfCAgIDQg Ky0KIGRyaXZlcnMveGVuL2h5cGVyX2RtYWJ1Zi9oeXBlcl9kbWFidWZfbXNnLmMgICAgICAgIHwg MTU1ICsrKysrKysrKysrKysrLS0tLS0tLQogLi4uL3hlbi9oeXBlcl9kbWFidWYveGVuL2h5cGVy X2RtYWJ1Zl94ZW5fY29tbS5jICAgfCAgNzUgKysrKy0tLS0tLQogLi4uL3hlbi9oeXBlcl9kbWFi dWYveGVuL2h5cGVyX2RtYWJ1Zl94ZW5fY29tbS5oICAgfCAgIDcgLQogNiBmaWxlcyBjaGFuZ2Vk LCAxNTIgaW5zZXJ0aW9ucygrKSwgMTA3IGRlbGV0aW9ucygtKQoKZGlmZiAtLWdpdCBhL2RyaXZl cnMveGVuL2h5cGVyX2RtYWJ1Zi9oeXBlcl9kbWFidWZfZHJ2LmMgYi9kcml2ZXJzL3hlbi9oeXBl cl9kbWFidWYvaHlwZXJfZG1hYnVmX2Rydi5jCmluZGV4IDA2OTgzMjcuLjcwYjQ4NzggMTAwNjQ0 Ci0tLSBhL2RyaXZlcnMveGVuL2h5cGVyX2RtYWJ1Zi9oeXBlcl9kbWFidWZfZHJ2LmMKKysrIGIv ZHJpdmVycy94ZW4vaHlwZXJfZG1hYnVmL2h5cGVyX2RtYWJ1Zl9kcnYuYwpAQCAtMSw1ICsxLDgg QEAKICNpbmNsdWRlIDxsaW51eC9pbml0Lmg+ICAgICAgIC8qIG1vZHVsZV9pbml0LCBtb2R1bGVf ZXhpdCAqLwogI2luY2x1ZGUgPGxpbnV4L21vZHVsZS5oPiAvKiB2ZXJzaW9uIGluZm8sIE1PRFVM RV9MSUNFTlNFLCBNT0RVTEVfQVVUSE9SLCBwcmludGsoKSAqLworI2luY2x1ZGUgPGxpbnV4L3dv cmtxdWV1ZS5oPgorI2luY2x1ZGUgPHhlbi9ncmFudF90YWJsZS5oPgorI2luY2x1ZGUgImh5cGVy X2RtYWJ1Zl9kcnYuaCIKICNpbmNsdWRlICJoeXBlcl9kbWFidWZfY29uZi5oIgogI2luY2x1ZGUg Imh5cGVyX2RtYWJ1Zl9saXN0LmgiCiAjaW5jbHVkZSAieGVuL2h5cGVyX2RtYWJ1Zl94ZW5fY29t bV9saXN0LmgiCkBAIC0xMCw2ICsxMyw4IEBAIE1PRFVMRV9BVVRIT1IoIklPVEctUEVELCBJTlRF TCIpOwogaW50IHJlZ2lzdGVyX2RldmljZSh2b2lkKTsKIGludCB1bnJlZ2lzdGVyX2RldmljZSh2 b2lkKTsKIAorc3RydWN0IGh5cGVyX2RtYWJ1Zl9wcml2YXRlIGh5cGVyX2RtYWJ1Zl9wcml2YXRl OworCiAvKj09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09 PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09Ki8KIHN0YXRpYyBp bnQgaHlwZXJfZG1hYnVmX2Rydl9pbml0KHZvaWQpCiB7CkBAIC0yNCw2ICsyOSwxMCBAQCBzdGF0 aWMgaW50IGh5cGVyX2RtYWJ1Zl9kcnZfaW5pdCh2b2lkKQogCiAJcHJpbnRrKCBLRVJOX05PVElD RSAiaW5pdGlhbGl6aW5nIGRhdGFiYXNlIGZvciBpbXBvcnRlZC9leHBvcnRlZCBkbWFidWZzXG4i KTsKIAorCS8qIGRldmljZSBzdHJ1Y3R1cmUgaW5pdGlhbGl6YXRpb24gKi8KKwkvKiBjdXJyZW50 bHkgb25seSBkb2VzIHdvcmstcXVldWUgaW5pdGlhbGl6YXRpb24gKi8KKwloeXBlcl9kbWFidWZf cHJpdmF0ZS53b3JrX3F1ZXVlID0gY3JlYXRlX3dvcmtxdWV1ZSgiaHlwZXJfZG1hYnVmX3dxdWV1 ZSIpOworCiAJcmV0ID0gaHlwZXJfZG1hYnVmX3RhYmxlX2luaXQoKTsKIAlpZiAocmV0IDwgMCkg ewogCQlyZXR1cm4gLUVJTlZBTDsKQEAgLTQ1LDYgKzU0LDEwIEBAIHN0YXRpYyB2b2lkIGh5cGVy X2RtYWJ1Zl9kcnZfZXhpdCh2b2lkKQogCWh5cGVyX2RtYWJ1Zl90YWJsZV9kZXN0cm95KCk7CiAJ aHlwZXJfZG1hYnVmX3JpbmdfdGFibGVfaW5pdCgpOwogCisJLyogZGVzdHJveSB3b3JrcXVldWUg Ki8KKwlpZiAoaHlwZXJfZG1hYnVmX3ByaXZhdGUud29ya19xdWV1ZSkKKwkJZGVzdHJveV93b3Jr cXVldWUoaHlwZXJfZG1hYnVmX3ByaXZhdGUud29ya19xdWV1ZSk7CisKIAlwcmludGsoIEtFUk5f Tk9USUNFICJkbWFfYnVmLXNyY19zaW5rIG1vZGVsOiBFeGl0aW5nIiApOwogCXVucmVnaXN0ZXJf ZGV2aWNlKCk7CiB9CmRpZmYgLS1naXQgYS9kcml2ZXJzL3hlbi9oeXBlcl9kbWFidWYvaHlwZXJf ZG1hYnVmX2Rydi5oIGIvZHJpdmVycy94ZW4vaHlwZXJfZG1hYnVmL2h5cGVyX2RtYWJ1Zl9kcnYu aAppbmRleCAyZGFkOWE2Li42MTQ1ZDI5IDEwMDY0NAotLS0gYS9kcml2ZXJzL3hlbi9oeXBlcl9k bWFidWYvaHlwZXJfZG1hYnVmX2Rydi5oCisrKyBiL2RyaXZlcnMveGVuL2h5cGVyX2RtYWJ1Zi9o eXBlcl9kbWFidWZfZHJ2LmgKQEAgLTEsNiArMSwxMSBAQAogI2lmbmRlZiBfX0xJTlVYX1BVQkxJ Q19IWVBFUl9ETUFCVUZfRFJWX0hfXwogI2RlZmluZSBfX0xJTlVYX1BVQkxJQ19IWVBFUl9ETUFC VUZfRFJWX0hfXwogCitzdHJ1Y3QgaHlwZXJfZG1hYnVmX3ByaXZhdGUgeworICAgICAgICBzdHJ1 Y3QgZGV2aWNlICpkZXZpY2U7CisJc3RydWN0IHdvcmtxdWV1ZV9zdHJ1Y3QgKndvcmtfcXVldWU7 Cit9OworCiB0eXBlZGVmIGludCAoKmh5cGVyX2RtYWJ1Zl9pb2N0bF90KSh2b2lkICpkYXRhKTsK IAogc3RydWN0IGh5cGVyX2RtYWJ1Zl9pb2N0bF9kZXNjIHsKZGlmZiAtLWdpdCBhL2RyaXZlcnMv eGVuL2h5cGVyX2RtYWJ1Zi9oeXBlcl9kbWFidWZfaW9jdGwuYyBiL2RyaXZlcnMveGVuL2h5cGVy X2RtYWJ1Zi9oeXBlcl9kbWFidWZfaW9jdGwuYwppbmRleCBhZjk0MzU5Li5lNGQ4MzE2IDEwMDY0 NAotLS0gYS9kcml2ZXJzL3hlbi9oeXBlcl9kbWFidWYvaHlwZXJfZG1hYnVmX2lvY3RsLmMKKysr IGIvZHJpdmVycy94ZW4vaHlwZXJfZG1hYnVmL2h5cGVyX2RtYWJ1Zl9pb2N0bC5jCkBAIC0xNSw5 ICsxNSw3IEBACiAjaW5jbHVkZSAieGVuL2h5cGVyX2RtYWJ1Zl94ZW5fY29tbV9saXN0LmgiCiAj aW5jbHVkZSAiaHlwZXJfZG1hYnVmX21zZy5oIgogCi1zdHJ1Y3QgaHlwZXJfZG1hYnVmX3ByaXZh dGUgewotCXN0cnVjdCBkZXZpY2UgKmRldmljZTsKLX0gaHlwZXJfZG1hYnVmX3ByaXZhdGU7Citl eHRlcm4gc3RydWN0IGh5cGVyX2RtYWJ1Zl9wcml2YXRlIGh5cGVyX2RtYWJ1Zl9wcml2YXRlOwog CiBzdGF0aWMgdWludDMyX3QgaHlwZXJfZG1hYnVmX2lkX2dlbih2b2lkKSB7CiAJLyogVE9ETzog YWRkIHByb3BlciBpbXBsZW1lbnRhdGlvbiAqLwpkaWZmIC0tZ2l0IGEvZHJpdmVycy94ZW4vaHlw ZXJfZG1hYnVmL2h5cGVyX2RtYWJ1Zl9tc2cuYyBiL2RyaXZlcnMveGVuL2h5cGVyX2RtYWJ1Zi9o eXBlcl9kbWFidWZfbXNnLmMKaW5kZXggMzIzN2U1MC4uMDE2NmU2MSAxMDA2NDQKLS0tIGEvZHJp dmVycy94ZW4vaHlwZXJfZG1hYnVmL2h5cGVyX2RtYWJ1Zl9tc2cuYworKysgYi9kcml2ZXJzL3hl bi9oeXBlcl9kbWFidWYvaHlwZXJfZG1hYnVmX21zZy5jCkBAIC0zLDEyICszLDIzIEBACiAjaW5j bHVkZSA8bGludXgvbW9kdWxlLmg+CiAjaW5jbHVkZSA8bGludXgvc2xhYi5oPgogI2luY2x1ZGUg PGxpbnV4L2RtYS1idWYuaD4KKyNpbmNsdWRlIDx4ZW4vZ3JhbnRfdGFibGUuaD4KKyNpbmNsdWRl IDxsaW51eC93b3JrcXVldWUuaD4KKyNpbmNsdWRlICJoeXBlcl9kbWFidWZfZHJ2LmgiCiAjaW5j bHVkZSAiaHlwZXJfZG1hYnVmX2ltcC5oIgogLy8jaW5jbHVkZSAiaHlwZXJfZG1hYnVmX3JlbW90 ZV9zeW5jLmgiCiAjaW5jbHVkZSAieGVuL2h5cGVyX2RtYWJ1Zl94ZW5fY29tbS5oIgogI2luY2x1 ZGUgImh5cGVyX2RtYWJ1Zl9tc2cuaCIKICNpbmNsdWRlICJoeXBlcl9kbWFidWZfbGlzdC5oIgog CitleHRlcm4gc3RydWN0IGh5cGVyX2RtYWJ1Zl9wcml2YXRlIGh5cGVyX2RtYWJ1Zl9wcml2YXRl OworCitzdHJ1Y3QgY21kX3Byb2Nlc3MgeworCXN0cnVjdCB3b3JrX3N0cnVjdCB3b3JrOworCXN0 cnVjdCBoeXBlcl9kbWFidWZfcmluZ19ycSAqcnE7CisJaW50IGRvbWlkOworfTsKKwogdm9pZCBo eXBlcl9kbWFidWZfY3JlYXRlX3JlcXVlc3Qoc3RydWN0IGh5cGVyX2RtYWJ1Zl9yaW5nX3JxICpy ZXF1ZXN0LAogCQkJCSAgICAgICAgZW51bSBoeXBlcl9kbWFidWZfY29tbWFuZCBjb21tYW5kLCBp bnQgKm9wZXJhbmRzKQogewpAQCAtNzEsMTggKzgyLDE3IEBAIHZvaWQgaHlwZXJfZG1hYnVmX2Ny ZWF0ZV9yZXF1ZXN0KHN0cnVjdCBoeXBlcl9kbWFidWZfcmluZ19ycSAqcmVxdWVzdCwKIAl9CiB9 CiAKLWludCBoeXBlcl9kbWFidWZfbXNnX3BhcnNlKGludCBkb21pZCwgc3RydWN0IGh5cGVyX2Rt YWJ1Zl9yaW5nX3JxICpyZXEpCit2b2lkIGNtZF9wcm9jZXNzX3dvcmsoc3RydWN0IHdvcmtfc3Ry dWN0ICp3b3JrKQogewotCXVpbnQzMl90IGksIHJldDsKIAlzdHJ1Y3QgaHlwZXJfZG1hYnVmX2lt cG9ydGVkX3NndF9pbmZvICppbXBvcnRlZF9zZ3RfaW5mbzsKLQlzdHJ1Y3QgaHlwZXJfZG1hYnVm X3NndF9pbmZvICpzZ3RfaW5mbzsKLQotCS8qIG1ha2Ugc3VyZSByZXEgaXMgbm90IE5VTEwgKG1h eSBub3QgYmUgbmVlZGVkKSAqLwotCWlmICghcmVxKSB7Ci0JCXJldHVybiAtRUlOVkFMOwotCX0K KyAgICAgICAgc3RydWN0IGh5cGVyX2RtYWJ1Zl9zZ3RfaW5mbyAqc2d0X2luZm87CisJc3RydWN0 IGNtZF9wcm9jZXNzICpwcm9jID0gY29udGFpbmVyX29mKHdvcmssIHN0cnVjdCBjbWRfcHJvY2Vz cywgd29yayk7CisJc3RydWN0IGh5cGVyX2RtYWJ1Zl9yaW5nX3JxICpyZXE7CisJaW50IGRvbWlk OworCWludCBpOwogCi0JcmVxLT5zdGF0dXMgPSBIWVBFUl9ETUFCVUZfUkVRX1BST0NFU1NFRDsK KwlyZXEgPSBwcm9jLT5ycTsKKwlkb21pZCA9IHByb2MtPmRvbWlkOwogCiAJc3dpdGNoIChyZXEt PmNvbW1hbmQpIHsKIAljYXNlIEhZUEVSX0RNQUJVRl9FWFBPUlQ6CkBAIC0xMTUsMzMgKzEyNSw2 IEBAIGludCBoeXBlcl9kbWFidWZfbXNnX3BhcnNlKGludCBkb21pZCwgc3RydWN0IGh5cGVyX2Rt YWJ1Zl9yaW5nX3JxICpyZXEpCiAJCWh5cGVyX2RtYWJ1Zl9yZWdpc3Rlcl9pbXBvcnRlZChpbXBv cnRlZF9zZ3RfaW5mbyk7CiAJCWJyZWFrOwogCi0JY2FzZSBIWVBFUl9ETUFCVUZfREVTVFJPWToK LQkJLyogZGVzdHJveSBzZ19saXN0IGZvciBoeXBlcl9kbWFidWZfaWQgb24gcmVtb3RlIHNpZGUg Ki8KLQkJLyogY29tbWFuZCA6IERNQUJVRl9ERVNUUk9ZLAotCQkgKiBvcGVyYW5kczAgOiBoeXBl cl9kbWFidWZfaWQKLQkJICovCi0KLQkJaW1wb3J0ZWRfc2d0X2luZm8gPQotCQkJaHlwZXJfZG1h YnVmX2ZpbmRfaW1wb3J0ZWQocmVxLT5vcGVyYW5kc1swXSk7Ci0KLQkJaWYgKGltcG9ydGVkX3Nn dF9pbmZvKSB7Ci0JCQloeXBlcl9kbWFidWZfY2xlYW51cF9pbXBvcnRlZF9wYWdlcyhpbXBvcnRl ZF9zZ3RfaW5mbyk7Ci0KLQkJCWh5cGVyX2RtYWJ1Zl9yZW1vdmVfaW1wb3J0ZWQocmVxLT5vcGVy YW5kc1swXSk7Ci0KLQkJCS8qIFRPRE86IGNsZWFudXAgc2d0IG9uIGltcG9ydGVyIHNpZGUgZXRj ICovCi0JCX0KLQotCQkvKiBOb3RpZnkgZXhwb3J0ZXIgdGhhdCBidWZmZXIgaXMgZnJlZWQgYW5k IGl0IGNhbiBjbGVhbnVwIGl0ICovCi0JCXJlcS0+c3RhdHVzID0gSFlQRVJfRE1BQlVGX1JFUV9O RUVEU19GT0xMT1dfVVA7Ci0JCXJlcS0+Y29tbWFuZCA9IEhZUEVSX0RNQUJVRl9ERVNUUk9ZX0ZJ TklTSDsKLQotI2lmIDAgLyogZnVuY3Rpb24gaXMgbm90IGltcGxlbWVudGVkIHlldCAqLwotCi0J CXJldCA9IGh5cGVyX2RtYWJ1Zl9kZXN0cm95X3NndChyZXEtPmh5cGVyX2RtYWJ1Zl9pZCk7Ci0j ZW5kaWYKLQkJYnJlYWs7Ci0KIAljYXNlIEhZUEVSX0RNQUJVRl9ERVNUUk9ZX0ZJTklTSDoKIAkJ LyogZGVzdHJveSBzZ19saXN0IGZvciBoeXBlcl9kbWFidWZfaWQgb24gbG9jYWwgc2lkZSAqLwog CQkvKiBjb21tYW5kIDogRE1BQlVGX0RFU1RST1lfRklOSVNILApAQCAtMTgwLDMzICsxNjMsMTAx IEBAIGludCBoeXBlcl9kbWFidWZfbXNnX3BhcnNlKGludCBkb21pZCwgc3RydWN0IGh5cGVyX2Rt YWJ1Zl9yaW5nX3JxICpyZXEpCiAJCSAqLwogCQlicmVhazsKIAotCS8qIHJlcXVlc3RpbmcgdGhl IG90aGVyIHNpZGUgdG8gc2V0dXAgYW5vdGhlciByaW5nIGNoYW5uZWwgZm9yIHJldmVyc2UgZGly ZWN0aW9uICovCi0JY2FzZSBIWVBFUl9ETUFCVUZfRVhQT1JURVJfUklOR19TRVRVUDoKLQkJLyog Y29tbWFuZDogSFlQRVJfRE1BQlVGX0VYUE9SVEVSX1JJTkdfU0VUVVAKLQkJICogbm8gb3BlcmFu ZHMgbmVlZGVkICovCisJY2FzZSBIWVBFUl9ETUFCVUZfSU1QT1JURVJfUklOR19TRVRVUDoKKwkJ LyogY29tbWFuZDogSFlQRVJfRE1BQlVGX0lNUE9SVEVSX1JJTkdfU0VUVVAgKi8KKwkJLyogbm8g b3BlcmFuZHMgbmVlZGVkICovCisJCWh5cGVyX2RtYWJ1Zl9pbXBvcnRlcl9yaW5nYnVmX2luaXQo ZG9taWQsIHJlcS0+b3BlcmFuZHNbMF0sIHJlcS0+b3BlcmFuZHNbMV0pOworCisJCWJyZWFrOwor CisJZGVmYXVsdDoKKwkJLyogc2hvdWxkbid0IGdldCBoZXJlICovCisJCS8qIG5vIG1hdGNoZWQg Y29tbWFuZCwgbm90aGluZyB0byBkby4uIGp1c3QgcmV0dXJuIGVycm9yICovCisJCWJyZWFrOwor CX0KKworCWtmcmVlKHJlcSk7CisJa2ZyZWUocHJvYyk7Cit9CisKK2ludCBoeXBlcl9kbWFidWZf bXNnX3BhcnNlKGludCBkb21pZCwgc3RydWN0IGh5cGVyX2RtYWJ1Zl9yaW5nX3JxICpyZXEpCit7 CisJc3RydWN0IGNtZF9wcm9jZXNzICpwcm9jOworCXN0cnVjdCBoeXBlcl9kbWFidWZfcmluZ19y cSAqdGVtcF9yZXE7CisJc3RydWN0IGh5cGVyX2RtYWJ1Zl9pbXBvcnRlZF9zZ3RfaW5mbyAqaW1w b3J0ZWRfc2d0X2luZm87CisJaW50IHJldDsKKworCWlmICghcmVxKSB7CisJCXByaW50aygicmVx dWVzdCBpcyBOVUxMXG4iKTsKKwkJcmV0dXJuIC1FSU5WQUw7CisJfQorCisJaWYgKChyZXEtPmNv bW1hbmQgPCBIWVBFUl9ETUFCVUZfRVhQT1JUKSB8fAorCQkocmVxLT5jb21tYW5kID4gSFlQRVJf RE1BQlVGX0lNUE9SVEVSX1JJTkdfU0VUVVApKSB7CisJCXByaW50aygiaW52YWxpZCBjb21tYW5k XG4iKTsKKwkJcmV0dXJuIC1FSU5WQUw7CisJfQorCisJcmVxLT5zdGF0dXMgPSBIWVBFUl9ETUFC VUZfUkVRX1BST0NFU1NFRDsKKworCS8qIEhZUEVSX0RNQUJVRl9FWFBPUlRFUl9SSU5HX1NFVFVQ IHJlcXVpcmVzIGltbWVkaWF0ZQorCSAqIGZvbGxvdyB1cCBzbyBjYW4ndCBiZSBwcm9jZXNzZWQg aW4gd29ya3F1ZXVlCisJICovCisJaWYgKHJlcS0+Y29tbWFuZCA9PSBIWVBFUl9ETUFCVUZfRVhQ T1JURVJfUklOR19TRVRVUCkgewogCQlyZXQgPSBoeXBlcl9kbWFidWZfZXhwb3J0ZXJfcmluZ2J1 Zl9pbml0KGRvbWlkLCAmcmVxLT5vcGVyYW5kc1swXSwgJnJlcS0+b3BlcmFuZHNbMV0pOwogCQlp ZiAocmV0IDwgMCkgewogCQkJcmVxLT5zdGF0dXMgPSBIWVBFUl9ETUFCVUZfUkVRX0VSUk9SOwot CQkJcmV0dXJuIC1FSU5WQUw7CiAJCX0KIAogCQlyZXEtPnN0YXR1cyA9IEhZUEVSX0RNQUJVRl9S RVFfTkVFRFNfRk9MTE9XX1VQOwogCQlyZXEtPmNvbW1hbmQgPSBIWVBFUl9ETUFCVUZfSU1QT1JU RVJfUklOR19TRVRVUDsKLQkJYnJlYWs7CiAKLQljYXNlIEhZUEVSX0RNQUJVRl9JTVBPUlRFUl9S SU5HX1NFVFVQOgotCQkvKiBjb21tYW5kOiBIWVBFUl9ETUFCVUZfSU1QT1JURVJfUklOR19TRVRV UCAqLwotCQkvKiBubyBvcGVyYW5kcyBuZWVkZWQgKi8KLQkJcmV0ID0gaHlwZXJfZG1hYnVmX2lt cG9ydGVyX3JpbmdidWZfaW5pdChkb21pZCwgcmVxLT5vcGVyYW5kc1swXSwgcmVxLT5vcGVyYW5k c1sxXSk7Ci0JCWlmIChyZXQgPCAwKQotCQkJcmV0dXJuIC1FSU5WQUw7CisJCXJldHVybiByZXEt PmNvbW1hbmQ7CisJfQogCi0JCWJyZWFrOworCS8qIEhZUEVSX0RNQUJVRl9ERVNUUk9ZIHJlcXVp cmVzIGltbWVkaWF0ZQorCSAqIGZvbGxvdyB1cCBzbyBjYW4ndCBiZSBwcm9jZXNzZWQgaW4gd29y a3F1ZXVlCisJICovCisJaWYgKHJlcS0+Y29tbWFuZCA9PSBIWVBFUl9ETUFCVUZfREVTVFJPWSkg eworCQkvKiBkZXN0cm95IHNnX2xpc3QgZm9yIGh5cGVyX2RtYWJ1Zl9pZCBvbiByZW1vdGUgc2lk ZSAqLworCQkvKiBjb21tYW5kIDogRE1BQlVGX0RFU1RST1ksCisJCSAqIG9wZXJhbmRzMCA6IGh5 cGVyX2RtYWJ1Zl9pZAorCQkgKi8KKwkJaW1wb3J0ZWRfc2d0X2luZm8gPQorCQkJaHlwZXJfZG1h YnVmX2ZpbmRfaW1wb3J0ZWQocmVxLT5vcGVyYW5kc1swXSk7CiAKLQlkZWZhdWx0OgotCQkvKiBu byBtYXRjaGVkIGNvbW1hbmQsIG5vdGhpbmcgdG8gZG8uLiBqdXN0IHJldHVybiBlcnJvciAqLwot CQlyZXR1cm4gLUVJTlZBTDsKKwkJaWYgKGltcG9ydGVkX3NndF9pbmZvKSB7CisJCQloeXBlcl9k bWFidWZfY2xlYW51cF9pbXBvcnRlZF9wYWdlcyhpbXBvcnRlZF9zZ3RfaW5mbyk7CisKKwkJCWh5 cGVyX2RtYWJ1Zl9yZW1vdmVfaW1wb3J0ZWQocmVxLT5vcGVyYW5kc1swXSk7CisKKwkJCS8qIFRP RE86IGNsZWFudXAgc2d0IG9uIGltcG9ydGVyIHNpZGUgZXRjICovCisJCX0KKworCQkvKiBOb3Rp ZnkgZXhwb3J0ZXIgdGhhdCBidWZmZXIgaXMgZnJlZWQgYW5kIGl0IGNhbiBjbGVhbnVwIGl0ICov CisJCXJlcS0+c3RhdHVzID0gSFlQRVJfRE1BQlVGX1JFUV9ORUVEU19GT0xMT1dfVVA7CisJCXJl cS0+Y29tbWFuZCA9IEhZUEVSX0RNQUJVRl9ERVNUUk9ZX0ZJTklTSDsKKworI2lmIDAgLyogZnVu Y3Rpb24gaXMgbm90IGltcGxlbWVudGVkIHlldCAqLworCisJCXJldCA9IGh5cGVyX2RtYWJ1Zl9k ZXN0cm95X3NndChyZXEtPmh5cGVyX2RtYWJ1Zl9pZCk7CisjZW5kaWYKKwkJcmV0dXJuIHJlcS0+ Y29tbWFuZDsKIAl9CiAKKwl0ZW1wX3JlcSA9IChzdHJ1Y3QgaHlwZXJfZG1hYnVmX3JpbmdfcnEg KilrbWFsbG9jKHNpemVvZigqdGVtcF9yZXEpLCBHRlBfS0VSTkVMKTsKKworCW1lbWNweSh0ZW1w X3JlcSwgcmVxLCBzaXplb2YoKnRlbXBfcmVxKSk7CisKKwlwcm9jID0gKHN0cnVjdCBjbWRfcHJv Y2VzcyAqKSBrY2FsbG9jKDEsIHNpemVvZihzdHJ1Y3QgY21kX3Byb2Nlc3MpLAorCQkJCQkJR0ZQ X0tFUk5FTCk7CisKKwlwcm9jLT5ycSA9IHRlbXBfcmVxOworCXByb2MtPmRvbWlkID0gZG9taWQ7 CisKKwlJTklUX1dPUksoJihwcm9jLT53b3JrKSwgY21kX3Byb2Nlc3Nfd29yayk7CisKKwlxdWV1 ZV93b3JrKGh5cGVyX2RtYWJ1Zl9wcml2YXRlLndvcmtfcXVldWUsICYocHJvYy0+d29yaykpOwor CiAJcmV0dXJuIHJlcS0+Y29tbWFuZDsKIH0KZGlmZiAtLWdpdCBhL2RyaXZlcnMveGVuL2h5cGVy X2RtYWJ1Zi94ZW4vaHlwZXJfZG1hYnVmX3hlbl9jb21tLmMgYi9kcml2ZXJzL3hlbi9oeXBlcl9k bWFidWYveGVuL2h5cGVyX2RtYWJ1Zl94ZW5fY29tbS5jCmluZGV4IDIyZjJlZjAuLjA1ODU1YmEx IDEwMDY0NAotLS0gYS9kcml2ZXJzL3hlbi9oeXBlcl9kbWFidWYveGVuL2h5cGVyX2RtYWJ1Zl94 ZW5fY29tbS5jCisrKyBiL2RyaXZlcnMveGVuL2h5cGVyX2RtYWJ1Zi94ZW4vaHlwZXJfZG1hYnVm X3hlbl9jb21tLmMKQEAgLTE0LDcgKzE0LDYgQEAKICNpbmNsdWRlICIuLi9oeXBlcl9kbWFidWZf bXNnLmgiCiAKIHN0YXRpYyBpbnQgZXhwb3J0X3JlcV9pZCA9IDA7Ci1zdGF0aWMgaW50IGltcG9y dF9yZXFfaWQgPSAwOwogCiBpbnQzMl90IGh5cGVyX2RtYWJ1Zl9nZXRfZG9taWQodm9pZCkKIHsK QEAgLTM3LDEyICszNiw2IEBAIGludCBoeXBlcl9kbWFidWZfbmV4dF9yZXFfaWRfZXhwb3J0KHZv aWQpCiAgICAgICAgIHJldHVybiBleHBvcnRfcmVxX2lkOwogfQogCi1pbnQgaHlwZXJfZG1hYnVm X25leHRfcmVxX2lkX2ltcG9ydCh2b2lkKQotewotICAgICAgICBpbXBvcnRfcmVxX2lkKys7Ci0g ICAgICAgIHJldHVybiBpbXBvcnRfcmVxX2lkOwotfQotCiAvKiBGb3Igbm93IGNhY2hlIGxhdGFz dCByaW5ncyBhcyBnbG9iYWwgdmFyaWFibGVzIFRPRE86IGtlZXAgdGhlbSBpbiBsaXN0Ki8KIHN0 YXRpYyBpcnFyZXR1cm5fdCBoeXBlcl9kbWFidWZfZnJvbnRfcmluZ19pc3IoaW50IGlycSwgdm9p ZCAqZGV2X2lkKTsKIHN0YXRpYyBpcnFyZXR1cm5fdCBoeXBlcl9kbWFidWZfYmFja19yaW5nX2lz cihpbnQgaXJxLCB2b2lkICpkZXZfaWQpOwpAQCAtODEsNyArNzQsOCBAQCBpbnQgaHlwZXJfZG1h YnVmX2V4cG9ydGVyX3JpbmdidWZfaW5pdChpbnQgcmRvbWFpbiwgZ3JhbnRfcmVmX3QgKnJlZmlk LCBpbnQgKnBvcgogCiAJYWxsb2NfdW5ib3VuZC5kb20gPSBET01JRF9TRUxGOwogCWFsbG9jX3Vu Ym91bmQucmVtb3RlX2RvbSA9IHJkb21haW47Ci0JcmV0ID0gSFlQRVJWSVNPUl9ldmVudF9jaGFu bmVsX29wKEVWVENITk9QX2FsbG9jX3VuYm91bmQsICZhbGxvY191bmJvdW5kKTsKKwlyZXQgPSBI WVBFUlZJU09SX2V2ZW50X2NoYW5uZWxfb3AoRVZUQ0hOT1BfYWxsb2NfdW5ib3VuZCwKKwkJCQkJ JmFsbG9jX3VuYm91bmQpOwogCWlmIChyZXQgIT0gMCkgewogCQlwcmludGsoIkNhbm5vdCBhbGxv Y2F0ZSBldmVudCBjaGFubmVsXG4iKTsKIAkJcmV0dXJuIC1FSU5WQUw7CkBAIC05Niw3ICs5MCw4 IEBAIGludCBoeXBlcl9kbWFidWZfZXhwb3J0ZXJfcmluZ2J1Zl9pbml0KGludCByZG9tYWluLCBn cmFudF9yZWZfdCAqcmVmaWQsIGludCAqcG9yCiAJCXByaW50aygiRmFpbGVkIHRvIHNldHVwIGV2 ZW50IGNoYW5uZWxcbiIpOwogCQljbG9zZS5wb3J0ID0gYWxsb2NfdW5ib3VuZC5wb3J0OwogCQlI WVBFUlZJU09SX2V2ZW50X2NoYW5uZWxfb3AoRVZUQ0hOT1BfY2xvc2UsICZjbG9zZSk7Ci0JCWdu dHRhYl9lbmRfZm9yZWlnbl9hY2Nlc3MocmluZ19pbmZvLT5ncmVmX3JpbmcsIDAsIHZpcnRfdG9f bWZuKHNoYXJlZF9yaW5nKSk7CisJCWdudHRhYl9lbmRfZm9yZWlnbl9hY2Nlc3MocmluZ19pbmZv LT5ncmVmX3JpbmcsIDAsCisJCQkJCXZpcnRfdG9fbWZuKHNoYXJlZF9yaW5nKSk7CiAJCXJldHVy biAtRUlOVkFMOwogCX0KIApAQCAtMTA4LDcgKzEwMyw4IEBAIGludCBoeXBlcl9kbWFidWZfZXhw b3J0ZXJfcmluZ2J1Zl9pbml0KGludCByZG9tYWluLCBncmFudF9yZWZfdCAqcmVmaWQsIGludCAq cG9yCiAJKnJlZmlkID0gcmluZ19pbmZvLT5ncmVmX3Jpbmc7CiAJKnBvcnQgPSByaW5nX2luZm8t PnBvcnQ7CiAKLQlwcmludGsoIiVzOiBhbGxvY2F0ZWQgZXZlbnRjaGFubmVsIGdyZWYgJWQgIHBv cnQ6ICVkICBpcnE6ICVkXG4iLCBfX2Z1bmNfXywKKwlwcmludGsoIiVzOiBhbGxvY2F0ZWQgZXZl bnRjaGFubmVsIGdyZWYgJWQgIHBvcnQ6ICVkICBpcnE6ICVkXG4iLAorCQlfX2Z1bmNfXywKIAkJ cmluZ19pbmZvLT5ncmVmX3JpbmcsCiAJCXJpbmdfaW5mby0+cG9ydCwKIAkJcmluZ19pbmZvLT5p cnEpOwpAQCAtMTYyLDggKzE1OCw5IEBAIGludCBoeXBlcl9kbWFidWZfaW1wb3J0ZXJfcmluZ2J1 Zl9pbml0KGludCBzZG9tYWluLCBncmFudF9yZWZfdCBncmVmLCBpbnQgcG9ydCkKIAogCUJBQ0tf UklOR19JTklUKCZyaW5nX2luZm8tPnJpbmdfYmFjaywgc3JpbmcsIFBBR0VfU0laRSk7CiAKLQly ZXQgPSBiaW5kX2ludGVyZG9tYWluX2V2dGNobl90b19pcnFoYW5kbGVyKHNkb21haW4sIHBvcnQs IGh5cGVyX2RtYWJ1Zl9iYWNrX3JpbmdfaXNyLCAwLAotCQkJCQkJICAgIE5VTEwsICh2b2lkKily aW5nX2luZm8pOworCXJldCA9IGJpbmRfaW50ZXJkb21haW5fZXZ0Y2huX3RvX2lycWhhbmRsZXIo c2RvbWFpbiwgcG9ydCwKKwkJCQkJCWh5cGVyX2RtYWJ1Zl9iYWNrX3JpbmdfaXNyLCAwLAorCQkJ CQkJTlVMTCwgKHZvaWQqKXJpbmdfaW5mbyk7CiAJaWYgKHJldCA8IDApIHsKIAkJcmV0dXJuIC1F SU5WQUw7CiAJfQpAQCAtMjE2LDI2ICsyMTMsMjAgQEAgaW50IGh5cGVyX2RtYWJ1Zl9zZW5kX3Jl cXVlc3QoaW50IGRvbWFpbiwgc3RydWN0IGh5cGVyX2RtYWJ1Zl9yaW5nX3JxICpyZXEpCiAJcmV0 dXJuIDA7CiB9CiAKLS8qIGNhbGxlZCBieSBpbnRlcnJ1cHQgKFdPUktRVUVVRSkgKi8KLWludCBo eXBlcl9kbWFidWZfc2VuZF9yZXNwb25zZShzdHJ1Y3QgaHlwZXJfZG1hYnVmX3JpbmdfcnAqIHJl c3BvbnNlLCBpbnQgZG9tYWluKQotewotCS8qIGFzIGEgaW1wb3J0ZXIgYW5kIGFzIGEgZXhwb3J0 ZXIgKi8KLQlyZXR1cm4gMDsKLX0KLQogLyogSVNSIGZvciByZXF1ZXN0IGZyb20gZXhwb3J0ZXIg KGFzIGFuIGltcG9ydGVyKSAqLwotc3RhdGljIGlycXJldHVybl90IGh5cGVyX2RtYWJ1Zl9iYWNr X3JpbmdfaXNyKGludCBpcnEsIHZvaWQgKmRldl9pZCkKK3N0YXRpYyBpcnFyZXR1cm5fdCBoeXBl cl9kbWFidWZfYmFja19yaW5nX2lzcihpbnQgaXJxLCB2b2lkICppbmZvKQogewogCVJJTkdfSURY IHJjLCBycDsKLQlzdHJ1Y3QgaHlwZXJfZG1hYnVmX3JpbmdfcnEgcmVxdWVzdDsKLQlzdHJ1Y3Qg aHlwZXJfZG1hYnVmX3JpbmdfcnAgcmVzcG9uc2U7CisJc3RydWN0IGh5cGVyX2RtYWJ1Zl9yaW5n X3JxIHJlcTsKKwlzdHJ1Y3QgaHlwZXJfZG1hYnVmX3JpbmdfcnAgcmVzcDsKKwogCWludCBub3Rp ZnksIG1vcmVfdG9fZG87CiAJaW50IHJldDsKLS8vCXN0cnVjdCBoeXBlcl9kbWFidWZfd29yayAq d29yazsKIAotCXN0cnVjdCBoeXBlcl9kbWFidWZfcmluZ19pbmZvX2ltcG9ydCAqcmluZ19pbmZv ID0gKHN0cnVjdCBoeXBlcl9kbWFidWZfcmluZ19pbmZvX2ltcG9ydCAqKWRldl9pZDsKKwlzdHJ1 Y3QgaHlwZXJfZG1hYnVmX3JpbmdfaW5mb19pbXBvcnQgKnJpbmdfaW5mbzsKIAlzdHJ1Y3QgaHlw ZXJfZG1hYnVmX2JhY2tfcmluZyAqcmluZzsKIAorCXJpbmdfaW5mbyA9IChzdHJ1Y3QgaHlwZXJf ZG1hYnVmX3JpbmdfaW5mb19pbXBvcnQgKilpbmZvOwogCXJpbmcgPSAmcmluZ19pbmZvLT5yaW5n X2JhY2s7CiAKIAlkbyB7CkBAIC0yNDYsMjIgKzIzNywxNiBAQCBzdGF0aWMgaXJxcmV0dXJuX3Qg aHlwZXJfZG1hYnVmX2JhY2tfcmluZ19pc3IoaW50IGlycSwgdm9pZCAqZGV2X2lkKQogCQkJaWYg KFJJTkdfUkVRVUVTVF9DT05TX09WRVJGTE9XKHJpbmcsIHJjKSkKIAkJCQlicmVhazsKIAotCQkJ bWVtY3B5KCZyZXF1ZXN0LCBSSU5HX0dFVF9SRVFVRVNUKHJpbmcsIHJjKSwgc2l6ZW9mKHJlcXVl c3QpKTsKKwkJCW1lbWNweSgmcmVxLCBSSU5HX0dFVF9SRVFVRVNUKHJpbmcsIHJjKSwgc2l6ZW9m KHJlcSkpOwogCQkJcHJpbnRrKCJHb3QgcmVxdWVzdFxuIik7CiAJCQlyaW5nLT5yZXFfY29ucyA9 ICsrcmM7CiAKLQkJCS8qIFRPRE86IHByb2JhYmx5IHVzaW5nIGxpbmtlZCBsaXN0IGZvciBtdWx0 aXBsZSByZXF1ZXN0cyB0aGVuIGxldAotCQkJICogYSB0YXNrIGluIGEgd29ya3F1ZXVlIHRvIHBy b2Nlc3MgdGhvc2UgaXMgYmV0dGVyIGlkZWEgYmVjdWFzZQotCQkJICogd2UgZG8gbm90IHdhbnQg dG8gc3RheSBpbiBJU1IgZm9yIGxvbmcuCi0JCQkgKi8KLQkJCXJldCA9IGh5cGVyX2RtYWJ1Zl9t c2dfcGFyc2UocmluZ19pbmZvLT5zZG9tYWluLCAmcmVxdWVzdCk7CisJCQlyZXQgPSBoeXBlcl9k bWFidWZfbXNnX3BhcnNlKHJpbmdfaW5mby0+c2RvbWFpbiwgJnJlcSk7CiAKIAkJCWlmIChyZXQg PiAwKSB7Ci0JCQkJLyogYnVpbGQgcmVzcG9uc2UgKi8KLQkJCQltZW1jcHkoJnJlc3BvbnNlLCAm cmVxdWVzdCwgc2l6ZW9mKHJlc3BvbnNlKSk7Ci0KLQkJCQkvKiB3ZSBzZW50IGJhY2sgbW9kaWZp ZWQgcmVxdWVzdCBhcyBhIHJlc3BvbnNlLi4gd2UgbWlnaHQganVzdCBuZWVkIHRvIGhhdmUgcmVx dWVzdCBvbmx5Li4qLwotCQkJCW1lbWNweShSSU5HX0dFVF9SRVNQT05TRShyaW5nLCByaW5nLT5y c3BfcHJvZF9wdnQpLCAmcmVzcG9uc2UsIHNpemVvZihyZXNwb25zZSkpOworCQkJCW1lbWNweSgm cmVzcCwgJnJlcSwgc2l6ZW9mKHJlc3ApKTsKKwkJCQltZW1jcHkoUklOR19HRVRfUkVTUE9OU0Uo cmluZywgcmluZy0+cnNwX3Byb2RfcHZ0KSwgJnJlc3AsCisJCQkJCQkJc2l6ZW9mKHJlc3ApKTsK IAkJCQlyaW5nLT5yc3BfcHJvZF9wdnQrKzsKIAogCQkJCVJJTkdfUFVTSF9SRVNQT05TRVNfQU5E X0NIRUNLX05PVElGWShyaW5nLCBub3RpZnkpOwpAQCAtMjgxLDE1ICsyNjYsMTcgQEAgc3RhdGlj IGlycXJldHVybl90IGh5cGVyX2RtYWJ1Zl9iYWNrX3JpbmdfaXNyKGludCBpcnEsIHZvaWQgKmRl dl9pZCkKIH0KIAogLyogSVNSIGZvciByZXNwb25zZXMgZnJvbSBpbXBvcnRlciAqLwotc3RhdGlj IGlycXJldHVybl90IGh5cGVyX2RtYWJ1Zl9mcm9udF9yaW5nX2lzcihpbnQgaXJxLCB2b2lkICpk ZXZfaWQpCitzdGF0aWMgaXJxcmV0dXJuX3QgaHlwZXJfZG1hYnVmX2Zyb250X3JpbmdfaXNyKGlu dCBpcnEsIHZvaWQgKmluZm8pCiB7CiAJLyogZnJvbnQgcmluZyBvbmx5IGNhcmUgYWJvdXQgcmVz cG9uc2UgZnJvbSBiYWNrICovCi0Jc3RydWN0IGh5cGVyX2RtYWJ1Zl9yaW5nX3JwICpyZXNwb25z ZTsKKwlzdHJ1Y3QgaHlwZXJfZG1hYnVmX3JpbmdfcnAgKnJlc3A7CiAJUklOR19JRFggaSwgcnA7 CiAJaW50IG1vcmVfdG9fZG8sIHJldDsKIAotCXN0cnVjdCBoeXBlcl9kbWFidWZfcmluZ19pbmZv X2V4cG9ydCAqcmluZ19pbmZvID0gKHN0cnVjdCBoeXBlcl9kbWFidWZfcmluZ19pbmZvX2V4cG9y dCAqKWRldl9pZDsKKwlzdHJ1Y3QgaHlwZXJfZG1hYnVmX3JpbmdfaW5mb19leHBvcnQgKnJpbmdf aW5mbzsKIAlzdHJ1Y3QgaHlwZXJfZG1hYnVmX2Zyb250X3JpbmcgKnJpbmc7CisKKwlyaW5nX2lu Zm8gPSAoc3RydWN0IGh5cGVyX2RtYWJ1Zl9yaW5nX2luZm9fZXhwb3J0ICopaW5mbzsKIAlyaW5n ID0gJnJpbmdfaW5mby0+cmluZ19mcm9udDsKIAogCWRvIHsKQEAgLTI5OCwyMCArMjg1LDE4IEBA IHN0YXRpYyBpcnFyZXR1cm5fdCBoeXBlcl9kbWFidWZfZnJvbnRfcmluZ19pc3IoaW50IGlycSwg dm9pZCAqZGV2X2lkKQogCQlmb3IgKGkgPSByaW5nLT5yc3BfY29uczsgaSAhPSBycDsgaSsrKSB7 CiAJCQl1bnNpZ25lZCBsb25nIGlkOwogCi0JCQlyZXNwb25zZSA9IFJJTkdfR0VUX1JFU1BPTlNF KHJpbmcsIGkpOwotCQkJaWQgPSByZXNwb25zZS0+cmVzcG9uc2VfaWQ7CisJCQlyZXNwID0gUklO R19HRVRfUkVTUE9OU0UocmluZywgaSk7CisJCQlpZCA9IHJlc3AtPnJlc3BvbnNlX2lkOwogCi0J CQlpZiAocmVzcG9uc2UtPnN0YXR1cyA9PSBIWVBFUl9ETUFCVUZfUkVRX05FRURTX0ZPTExPV19V UCkgeworCQkJaWYgKHJlc3AtPnN0YXR1cyA9PSBIWVBFUl9ETUFCVUZfUkVRX05FRURTX0ZPTExP V19VUCkgewogCQkJCS8qIHBhcnNpbmcgcmVzcG9uc2UgKi8KLQkJCQlyZXQgPSBoeXBlcl9kbWFi dWZfbXNnX3BhcnNlKHJpbmdfaW5mby0+cmRvbWFpbiwgKHN0cnVjdCBoeXBlcl9kbWFidWZfcmlu Z19ycSopcmVzcG9uc2UpOworCQkJCXJldCA9IGh5cGVyX2RtYWJ1Zl9tc2dfcGFyc2UocmluZ19p bmZvLT5yZG9tYWluLAorCQkJCQkJCShzdHJ1Y3QgaHlwZXJfZG1hYnVmX3JpbmdfcnEgKilyZXNw KTsKIAogCQkJCWlmIChyZXQgPCAwKSB7CiAJCQkJCXByaW50aygiZ2V0dGluZyBlcnJvciB3aGls ZSBwYXJzaW5nIHJlc3BvbnNlXG4iKTsKIAkJCQl9Ci0JCQl9IGVsc2UgaWYgKHJlc3BvbnNlLT5z dGF0dXMgPT0gSFlQRVJfRE1BQlVGX1JFUV9FUlJPUikgewotCQkJCXByaW50aygicmVtb3RlIGRv bWFpbiAlZCBjb3VsZG4ndCBwcm9jZXNzIHJlcXVlc3QgJWRcbiIsIHJpbmdfaW5mby0+cmRvbWFp biwgcmVzcG9uc2UtPmNvbW1hbmQpOwogCQkJfQotCiAJCX0KIAogCQlyaW5nLT5yc3BfY29ucyA9 IGk7CmRpZmYgLS1naXQgYS9kcml2ZXJzL3hlbi9oeXBlcl9kbWFidWYveGVuL2h5cGVyX2RtYWJ1 Zl94ZW5fY29tbS5oIGIvZHJpdmVycy94ZW4vaHlwZXJfZG1hYnVmL3hlbi9oeXBlcl9kbWFidWZf eGVuX2NvbW0uaAppbmRleCAyNzU0OTE3Li40YWQwNTI5IDEwMDY0NAotLS0gYS9kcml2ZXJzL3hl bi9oeXBlcl9kbWFidWYveGVuL2h5cGVyX2RtYWJ1Zl94ZW5fY29tbS5oCisrKyBiL2RyaXZlcnMv eGVuL2h5cGVyX2RtYWJ1Zi94ZW4vaHlwZXJfZG1hYnVmX3hlbl9jb21tLmgKQEAgLTM2LDE3ICsz NiwxMCBAQCBzdHJ1Y3QgaHlwZXJfZG1hYnVmX3JpbmdfaW5mb19pbXBvcnQgewogICAgICAgICBz dHJ1Y3QgaHlwZXJfZG1hYnVmX2JhY2tfcmluZyByaW5nX2JhY2s7CiB9OwogCi0vL3N0cnVjdCBo eXBlcl9kbWFidWZfd29yayB7Ci0vLwloeXBlcl9kbWFidWZfcmluZ19ycSByZXF1cmVzdDsKLS8v CXN0cnVjdCB3b3JrX3N0cnVjdCBtc2dfcGFyc2U7Ci0vL307Ci0KIGludDMyX3QgaHlwZXJfZG1h YnVmX2dldF9kb21pZCh2b2lkKTsKIAogaW50IGh5cGVyX2RtYWJ1Zl9uZXh0X3JlcV9pZF9leHBv cnQodm9pZCk7CiAKLWludCBoeXBlcl9kbWFidWZfbmV4dF9yZXFfaWRfaW1wb3J0KHZvaWQpOwot CiAvKiBleHBvcnRlciBuZWVkcyB0byBnZW5lcmF0ZWQgaW5mbyBmb3IgcGFnZSBzaGFyaW5nICov CiBpbnQgaHlwZXJfZG1hYnVmX2V4cG9ydGVyX3JpbmdidWZfaW5pdChpbnQgcmRvbWFpbiwgZ3Jh bnRfcmVmX3QgKmdyZWYsIGludCAqcG9ydCk7CiAKLS0gCjIuNy40CgpfX19fX19fX19fX19fX19f X19fX19fX19fX19fX19fX19fX19fX19fX19fX19fXwpkcmktZGV2ZWwgbWFpbGluZyBsaXN0CmRy aS1kZXZlbEBsaXN0cy5mcmVlZGVza3RvcC5vcmcKaHR0cHM6Ly9saXN0cy5mcmVlZGVza3RvcC5v cmcvbWFpbG1hbi9saXN0aW5mby9kcmktZGV2ZWwK