From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-8.6 required=3.0 tests=DKIM_SIGNED,DKIM_VALID, DKIM_VALID_AU,HEADER_FROM_DIFFERENT_DOMAINS,INCLUDES_PATCH,MAILING_LIST_MULTI, SIGNED_OFF_BY,SPF_PASS,URIBL_BLOCKED,USER_AGENT_MUTT autolearn=ham autolearn_force=no version=3.4.0 Received: from mail.kernel.org (mail.kernel.org [198.145.29.99]) by smtp.lore.kernel.org (Postfix) with ESMTP id 3D7DDC43381 for ; Tue, 19 Feb 2019 00:31:36 +0000 (UTC) Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by mail.kernel.org (Postfix) with ESMTP id D94B6208E4 for ; Tue, 19 Feb 2019 00:31:35 +0000 (UTC) Authentication-Results: mail.kernel.org; dkim=pass (1024-bit key) header.d=ideasonboard.com header.i=@ideasonboard.com header.b="PDt6Hhzb" Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1728244AbfBSAbf (ORCPT ); Mon, 18 Feb 2019 19:31:35 -0500 Received: from perceval.ideasonboard.com ([213.167.242.64]:40626 "EHLO perceval.ideasonboard.com" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1726220AbfBSAbf (ORCPT ); Mon, 18 Feb 2019 19:31:35 -0500 Received: from pendragon.ideasonboard.com (91-152-6-44.elisa-laajakaista.fi [91.152.6.44]) by perceval.ideasonboard.com (Postfix) with ESMTPSA id B136D2D5; Tue, 19 Feb 2019 01:31:30 +0100 (CET) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=ideasonboard.com; s=mail; t=1550536291; bh=CpWtqtBygkkkX4S9L5B5h3Q5gWKM/I5zdU2ntugK2JI=; h=Date:From:To:Cc:Subject:References:In-Reply-To:From; b=PDt6HhzbJj2k8/XqxLizw1rXjVqY5cSUq17UXTrGZTZ85/Mlg0OAZxOPDXBwtk7mk muSyJRaQunCDz9x47jQyh0NqvuWCpbGXMEtEKruGo4JJkp7d1fMc52KfrlylatAzlD BR57LKxXGQdrh2SPdNWNuRjaNIARU194xjiJYBDM= Date: Tue, 19 Feb 2019 02:31:26 +0200 From: Laurent Pinchart To: Kieran Bingham Cc: Laurent Pinchart , linux-media@vger.kernel.org, dri-devel@lists.freedesktop.org Subject: Re: [PATCH v4 7/7] media: vsp1: Provide a writeback video device Message-ID: <20190219003126.GE5082@pendragon.ideasonboard.com> References: <20190217024852.23328-1-laurent.pinchart+renesas@ideasonboard.com> <20190217024852.23328-8-laurent.pinchart+renesas@ideasonboard.com> <42e86cc1-ff3d-1e98-9da6-b072497dbed2@ideasonboard.com> MIME-Version: 1.0 Content-Type: text/plain; charset=utf-8 Content-Disposition: inline In-Reply-To: <42e86cc1-ff3d-1e98-9da6-b072497dbed2@ideasonboard.com> User-Agent: Mutt/1.10.1 (2018-07-13) Sender: linux-media-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-media@vger.kernel.org Hi Kieran, On Sun, Feb 17, 2019 at 08:06:32PM +0000, Kieran Bingham wrote: > On 17/02/2019 02:48, Laurent Pinchart wrote: > > From: Kieran Bingham > > > > When the VSP1 is used in an active display pipeline, the output of the > > WPF can supply the LIF entity directly and simultaneously write to > > memory. > > > > Support this functionality in the VSP1 driver through a V4L2 video > > device node connected to the WPF. > > > > The writeback video node support RGB formats only due to the WPF > > outputting RGB to the LIF. The pixel format can otherwise be configured > > freely. > > > > The resolution of the captured frames are set by the display mode. A > > different resolution can be selected on the video node, in which case > > cropping or composing will be performed. > > > > Signed-off-by: Kieran Bingham > > Signed-off-by: Laurent Pinchart > > For your changes, > > With the documentation updated for vsp1_dl_body_write_patch(), > > Reviewed-by: Kieran Bingham > > > --- > > Changes since v3: > > > > - Infer has_writeback from the number of LIFs and the generation > > - Remove vsp1_video::is_writeback > > - Describe writeback video nodes as 'writeback' > > - Add mechanism to patch active display lists > > - Handle writeback format restrictions > > - Don't wait for next page flip before completing writeback buffer > > This is a nice addition. Thank you. It was the hard part :) > > - Periods at the end of sentences. > > You also fix writeback for the bitrot that the previous sets had now > that we have partition handling. > > Interestingly my local implementation for this bitrot was just to > allocate a table for a single partition. I like your implementation > better :) Thank you. > > Changes since v2: > > - Rebased to v4.12-rc1 > > > > Changes since RFC > > - Fix checkpatch.pl warnings > > - Adapt to use a single source pad for the Writeback and LIF > > - Use WPF properties to determine when to create links instead of VSP > > - Remove incorrect vsp1_video_verify_format() changes > > - Spelling and grammar fixes > > --- > > drivers/media/platform/vsp1/vsp1_dl.c | 83 +++++++++++++ > > drivers/media/platform/vsp1/vsp1_dl.h | 4 + > > drivers/media/platform/vsp1/vsp1_drm.c | 14 ++- > > drivers/media/platform/vsp1/vsp1_drv.c | 17 ++- > > drivers/media/platform/vsp1/vsp1_pipe.c | 5 + > > drivers/media/platform/vsp1/vsp1_pipe.h | 6 + > > drivers/media/platform/vsp1/vsp1_rwpf.h | 2 + > > drivers/media/platform/vsp1/vsp1_video.c | 150 +++++++++++++++++++++-- > > drivers/media/platform/vsp1/vsp1_video.h | 6 + > > drivers/media/platform/vsp1/vsp1_wpf.c | 49 ++++++-- > > 10 files changed, 318 insertions(+), 18 deletions(-) > > > > diff --git a/drivers/media/platform/vsp1/vsp1_dl.c b/drivers/media/platform/vsp1/vsp1_dl.c > > index 886b3a69d329..591544382946 100644 > > --- a/drivers/media/platform/vsp1/vsp1_dl.c > > +++ b/drivers/media/platform/vsp1/vsp1_dl.c > > @@ -115,6 +115,12 @@ struct vsp1_dl_body { > > > > unsigned int num_entries; > > unsigned int max_entries; > > + > > + unsigned int num_patches; > > + struct { > > + struct vsp1_dl_entry *entry; > > + u32 data; > > + } patches[2]; > > What's the significance of [2] ? > Perhaps it will be clear what two entry's support patching later... > > Ok - yes - it's to patch both the Writeback enable and the display start > enable. Yes, we only need two registers. This is a bit of a hack, I'd like to come up with a better API, but making it generic will be unneedingly costly. > > }; > > > > /** > > @@ -361,6 +367,7 @@ void vsp1_dl_body_put(struct vsp1_dl_body *dlb) > > return; > > > > dlb->num_entries = 0; > > + dlb->num_patches = 0; > > > > spin_lock_irqsave(&dlb->pool->lock, flags); > > list_add_tail(&dlb->free, &dlb->pool->free); > > @@ -388,6 +395,37 @@ void vsp1_dl_body_write(struct vsp1_dl_body *dlb, u32 reg, u32 data) > > dlb->num_entries++; > > } > > > > +/** > > + * vsp1_dl_body_write - Write a register to a display list body > > s/_write/_write_patch/ Oops. I forgot to update the documentation :-/ > "Store an update to an existing register for handling at display-start > interrupt...."? (or as you see fit) The function writes a register and stores the update. I'll fix the documentation. /** * vsp1_dl_body_write_patch - Write a register to a display list body with an * update for the next vblank * @dlb: The body * @reg: The register address * @data: The register value * @patch: The register value for the next vblank * * Display lists in continuous mode are re-used by the hardware for successive * frames until a new display list is committed. Changing the VSP configuration * normally requires creating and committing a new display list. This function * offers an alternative race-free way by writing a @value to the @register in * the display list body, along with an updated @patch value to be written to * the VSP one vblank after the display list is committed. * * The maximum number of patch entries that can be written in a body is 2. */ > > + * @dlb: The body > > + * @reg: The register address > > + * @data: The register value > > + * > > + patch: The updated value to modify... > > > + * Write the given register and value to the display list body. The maximum > > + * number of entries that can be written in a body is specified when the body is > > + * allocated by vsp1_dl_body_alloc(). > > I guess this is a copy/paste hangover. > > How about: > > "Display lists in continuous mode are re-used by the hardware for > successive frames without needed to recommit a new display list. A patch > allows us to apply small changes to the display list before it is reused > to allow minor configuration changes without involving a full rewrite of > the list or facing a race at commit." > > (Or however you see fit...) > > > + */ > > +void vsp1_dl_body_write_patch(struct vsp1_dl_body *dlb, u32 reg, u32 data, > > + u32 patch) > > +{ > > + if (WARN_ONCE(dlb->num_entries >= dlb->max_entries, > > + "DLB size exceeded (max %u)", dlb->max_entries)) > > + return; > > + > > + if (WARN_ONCE(dlb->num_patches >= ARRAY_SIZE(dlb->patches), > > + "DLB patches size exceeded (max %lu)", > > + ARRAY_SIZE(dlb->patches))) > > + return; > > + > > + dlb->patches[dlb->num_patches].entry = &dlb->entries[dlb->num_entries]; > > + dlb->patches[dlb->num_patches].data = patch; > > + dlb->num_patches++; > > + > > + dlb->entries[dlb->num_entries].addr = reg; > > + dlb->entries[dlb->num_entries].data = data; > > + dlb->num_entries++; > > +} > > + > > /* ----------------------------------------------------------------------------- > > * Display List Extended Command Management > > */ > > @@ -652,6 +690,7 @@ static void __vsp1_dl_list_put(struct vsp1_dl_list *dl) > > * has at least one body, thus we reinitialise the entries list. > > */ > > dl->body0->num_entries = 0; > > + dl->body0->num_patches = 0; > > > > list_add_tail(&dl->list, &dl->dlm->free); > > } > > @@ -930,6 +969,36 @@ void vsp1_dl_list_commit(struct vsp1_dl_list *dl, unsigned int dl_flags) > > * Display List Manager > > */ > > > > +/** > > + * vsp1_dlm_irq_display_start - Display list handler for the display start > > + * interrupt > > + * @dlm: the display list manager > > + * > > + * Apply all patches registered for the active display list. This is used to > > + * disable writeback for the next frame. > > + */ > > +void vsp1_dlm_irq_display_start(struct vsp1_dl_manager *dlm) > > +{ > > + struct vsp1_dl_body *dlb; > > + struct vsp1_dl_list *dl; > > + unsigned int i; > > + > > + spin_lock(&dlm->lock); > > + > > + dl = dlm->active; > > + if (!dl) > > + goto done; > > + > > + list_for_each_entry(dlb, &dl->bodies, list) { > > + for (i = 0; i < dlb->num_patches; ++i) > > + dlb->patches[i].entry->data = dlb->patches[i].data; > > + dlb->num_patches = 0; > > + } > > + > > +done: > > + spin_unlock(&dlm->lock); > > +} > > + > > /** > > * vsp1_dlm_irq_frame_end - Display list handler for the frame end interrupt > > * @dlm: the display list manager > > @@ -947,6 +1016,9 @@ void vsp1_dl_list_commit(struct vsp1_dl_list *dl, unsigned int dl_flags) > > * > > * The VSP1_DL_FRAME_END_INTERNAL flag indicates that the display list that just > > * became active had been queued with the internal notification flag. > > + * > > + * The VSP1_DL_FRAME_END_WRITEBACK flag indicates that the previously active > > + * display list had been queued with the writeback flag. > > */ > > unsigned int vsp1_dlm_irq_frame_end(struct vsp1_dl_manager *dlm) > > { > > @@ -984,6 +1056,17 @@ unsigned int vsp1_dlm_irq_frame_end(struct vsp1_dl_manager *dlm) > > if (status & VI6_STATUS_FLD_STD(dlm->index)) > > goto done; > > > > + /* > > + * If the active display list has the writeback flag set, the frame > > + * completion marks the end of the writeback capture. Return the > > + * VSP1_DL_FRAME_END_WRITEBACK flag and reset the display list's > > + * writeback flag. > > + */ > > + if (dlm->active && (dlm->active->flags & VSP1_DL_FRAME_END_WRITEBACK)) { > > + flags |= VSP1_DL_FRAME_END_WRITEBACK; > > + dlm->active->flags &= ~VSP1_DL_FRAME_END_WRITEBACK; > > + } > > + > > /* > > * The device starts processing the queued display list right after the > > * frame end interrupt. The display list thus becomes active. > > diff --git a/drivers/media/platform/vsp1/vsp1_dl.h b/drivers/media/platform/vsp1/vsp1_dl.h > > index e0fdb145e6ed..cbaa0bf0cbc2 100644 > > --- a/drivers/media/platform/vsp1/vsp1_dl.h > > +++ b/drivers/media/platform/vsp1/vsp1_dl.h > > @@ -19,6 +19,7 @@ struct vsp1_dl_manager; > > > > #define VSP1_DL_FRAME_END_COMPLETED BIT(0) > > #define VSP1_DL_FRAME_END_INTERNAL BIT(1) > > +#define VSP1_DL_FRAME_END_WRITEBACK BIT(2) > > > > /** > > * struct vsp1_dl_ext_cmd - Extended Display command > > @@ -54,6 +55,7 @@ struct vsp1_dl_manager *vsp1_dlm_create(struct vsp1_device *vsp1, > > unsigned int prealloc); > > void vsp1_dlm_destroy(struct vsp1_dl_manager *dlm); > > void vsp1_dlm_reset(struct vsp1_dl_manager *dlm); > > +void vsp1_dlm_irq_display_start(struct vsp1_dl_manager *dlm); > > unsigned int vsp1_dlm_irq_frame_end(struct vsp1_dl_manager *dlm); > > struct vsp1_dl_body *vsp1_dlm_dl_body_get(struct vsp1_dl_manager *dlm); > > > > @@ -71,6 +73,8 @@ struct vsp1_dl_body *vsp1_dl_body_get(struct vsp1_dl_body_pool *pool); > > void vsp1_dl_body_put(struct vsp1_dl_body *dlb); > > > > void vsp1_dl_body_write(struct vsp1_dl_body *dlb, u32 reg, u32 data); > > +void vsp1_dl_body_write_patch(struct vsp1_dl_body *dlb, u32 reg, u32 data, > > + u32 patch); > > int vsp1_dl_list_add_body(struct vsp1_dl_list *dl, struct vsp1_dl_body *dlb); > > int vsp1_dl_list_add_chain(struct vsp1_dl_list *head, struct vsp1_dl_list *dl); > > > > diff --git a/drivers/media/platform/vsp1/vsp1_drm.c b/drivers/media/platform/vsp1/vsp1_drm.c > > index 9d20ef5cd5f8..e9d0ce432a2c 100644 > > --- a/drivers/media/platform/vsp1/vsp1_drm.c > > +++ b/drivers/media/platform/vsp1/vsp1_drm.c > > @@ -23,6 +23,7 @@ > > #include "vsp1_pipe.h" > > #include "vsp1_rwpf.h" > > #include "vsp1_uif.h" > > +#include "vsp1_video.h" > > > > #define BRX_NAME(e) (e)->type == VSP1_ENTITY_BRU ? "BRU" : "BRS" > > > > @@ -34,7 +35,7 @@ static void vsp1_du_pipeline_frame_end(struct vsp1_pipeline *pipe, > > unsigned int completion) > > { > > struct vsp1_drm_pipeline *drm_pipe = to_vsp1_drm_pipeline(pipe); > > - bool complete = completion == VSP1_DL_FRAME_END_COMPLETED; > > + bool complete = completion & VSP1_DL_FRAME_END_COMPLETED; > > > > if (drm_pipe->du_complete) { > > struct vsp1_entity *uif = drm_pipe->uif; > > @@ -48,6 +49,9 @@ static void vsp1_du_pipeline_frame_end(struct vsp1_pipeline *pipe, > > drm_pipe->force_brx_release = false; > > wake_up(&drm_pipe->wait_queue); > > } > > + > > + if (completion & VSP1_DL_FRAME_END_WRITEBACK) > > + vsp1_video_wb_frame_end(pipe->output->video); > > } > > > > /* ----------------------------------------------------------------------------- > > @@ -541,6 +545,8 @@ static void vsp1_du_pipeline_configure(struct vsp1_pipeline *pipe) > > > > if (drm_pipe->force_brx_release) > > dl_flags |= VSP1_DL_FRAME_END_INTERNAL; > > + if (pipe->output->writeback) > > + dl_flags |= VSP1_DL_FRAME_END_WRITEBACK; > > > > dl = vsp1_dl_list_get(pipe->output->dlm); > > dlb = vsp1_dl_list_get_body0(dl); > > @@ -859,8 +865,14 @@ void vsp1_du_atomic_flush(struct device *dev, unsigned int pipe_index, > > drm_pipe->crc = cfg->crc; > > > > mutex_lock(&vsp1->drm->lock); > > + > > + /* If we have a writeback node attached, update the video buffers. */ > > + if (pipe->output->video) > > + vsp1_video_wb_prepare(pipe->output->video); > > + > > vsp1_du_pipeline_setup_inputs(vsp1, pipe); > > vsp1_du_pipeline_configure(pipe); > > + > > mutex_unlock(&vsp1->drm->lock); > > } > > EXPORT_SYMBOL_GPL(vsp1_du_atomic_flush); > > diff --git a/drivers/media/platform/vsp1/vsp1_drv.c b/drivers/media/platform/vsp1/vsp1_drv.c > > index c650e45bb0ad..235febd18ffa 100644 > > --- a/drivers/media/platform/vsp1/vsp1_drv.c > > +++ b/drivers/media/platform/vsp1/vsp1_drv.c > > @@ -63,6 +63,21 @@ static irqreturn_t vsp1_irq_handler(int irq, void *data) > > vsp1_pipeline_frame_end(wpf->entity.pipe); > > ret = IRQ_HANDLED; > > } > > + > > + /* > > + * Process the display start interrupt after the frame end > > + * interrupt to make sure the display list queue is correctly > > + * updated when processing the display start. > > + */ > > + if (wpf->has_writeback) { > > + status = vsp1_read(vsp1, VI6_DISP_IRQ_STA(i)); > > + vsp1_write(vsp1, VI6_DISP_IRQ_STA(i), ~status & mask); > > + > > + if (status & VI6_DISP_IRQ_STA_DST) { > > + vsp1_pipeline_display_start(wpf->entity.pipe); > > + ret = IRQ_HANDLED; > > + } > > + } > > } > > > > return ret; > > @@ -435,7 +450,7 @@ static int vsp1_create_entities(struct vsp1_device *vsp1) > > vsp1->wpf[i] = wpf; > > list_add_tail(&wpf->entity.list_dev, &vsp1->entities); > > > > - if (vsp1->info->uapi) { > > + if (vsp1->info->uapi || wpf->has_writeback) { > > struct vsp1_video *video = vsp1_video_create(vsp1, wpf); > > > > if (IS_ERR(video)) { > > diff --git a/drivers/media/platform/vsp1/vsp1_pipe.c b/drivers/media/platform/vsp1/vsp1_pipe.c > > index 54ff539ffea0..016800c45bc1 100644 > > --- a/drivers/media/platform/vsp1/vsp1_pipe.c > > +++ b/drivers/media/platform/vsp1/vsp1_pipe.c > > @@ -309,6 +309,11 @@ bool vsp1_pipeline_ready(struct vsp1_pipeline *pipe) > > return pipe->buffers_ready == mask; > > } > > > > +void vsp1_pipeline_display_start(struct vsp1_pipeline *pipe) > > +{ > > + vsp1_dlm_irq_display_start(pipe->output->dlm); > > +} > > + > > void vsp1_pipeline_frame_end(struct vsp1_pipeline *pipe) > > { > > unsigned int flags; > > diff --git a/drivers/media/platform/vsp1/vsp1_pipe.h b/drivers/media/platform/vsp1/vsp1_pipe.h > > index ae646c9ef337..82d51b891f1e 100644 > > --- a/drivers/media/platform/vsp1/vsp1_pipe.h > > +++ b/drivers/media/platform/vsp1/vsp1_pipe.h > > @@ -47,6 +47,11 @@ struct vsp1_format_info { > > bool alpha; > > }; > > > > +static inline bool vsp1_format_is_rgb(const struct vsp1_format_info *info) > > +{ > > + return info->mbus == MEDIA_BUS_FMT_ARGB8888_1X32; > > +} > > + > > enum vsp1_pipeline_state { > > VSP1_PIPELINE_STOPPED, > > VSP1_PIPELINE_RUNNING, > > @@ -158,6 +163,7 @@ bool vsp1_pipeline_stopped(struct vsp1_pipeline *pipe); > > int vsp1_pipeline_stop(struct vsp1_pipeline *pipe); > > bool vsp1_pipeline_ready(struct vsp1_pipeline *pipe); > > > > +void vsp1_pipeline_display_start(struct vsp1_pipeline *pipe); > > void vsp1_pipeline_frame_end(struct vsp1_pipeline *pipe); > > > > void vsp1_pipeline_propagate_alpha(struct vsp1_pipeline *pipe, > > diff --git a/drivers/media/platform/vsp1/vsp1_rwpf.h b/drivers/media/platform/vsp1/vsp1_rwpf.h > > index 70742ecf766f..910990b27617 100644 > > --- a/drivers/media/platform/vsp1/vsp1_rwpf.h > > +++ b/drivers/media/platform/vsp1/vsp1_rwpf.h > > @@ -35,6 +35,7 @@ struct vsp1_rwpf { > > struct v4l2_ctrl_handler ctrls; > > > > struct vsp1_video *video; > > + bool has_writeback; > > > > unsigned int max_width; > > unsigned int max_height; > > @@ -61,6 +62,7 @@ struct vsp1_rwpf { > > } flip; > > > > struct vsp1_rwpf_memory mem; > > + bool writeback; > > > > struct vsp1_dl_manager *dlm; > > }; > > diff --git a/drivers/media/platform/vsp1/vsp1_video.c b/drivers/media/platform/vsp1/vsp1_video.c > > index 8feaa8d89fe8..0ac3430292d0 100644 > > --- a/drivers/media/platform/vsp1/vsp1_video.c > > +++ b/drivers/media/platform/vsp1/vsp1_video.c > > @@ -34,7 +34,6 @@ > > #include "vsp1_uds.h" > > #include "vsp1_video.h" > > > > -#define VSP1_VIDEO_DEF_FORMAT V4L2_PIX_FMT_YUYV > > #define VSP1_VIDEO_DEF_WIDTH 1024 > > #define VSP1_VIDEO_DEF_HEIGHT 768 > > > > @@ -45,6 +44,14 @@ > > * Helper functions > > */ > > > > +static inline unsigned int vsp1_video_default_format(struct vsp1_video *video) > > +{ > > + if (video->rwpf->has_writeback) > > + return V4L2_PIX_FMT_RGB24; > > + else > > + return V4L2_PIX_FMT_YUYV; > > +} > > + > > static struct v4l2_subdev * > > vsp1_video_remote_subdev(struct media_pad *local, u32 *pad) > > { > > @@ -113,11 +120,13 @@ static int __vsp1_video_try_format(struct vsp1_video *video, > > > > /* > > * Retrieve format information and select the default format if the > > - * requested format isn't supported. > > + * requested format isn't supported. Writeback video nodes only support > > + * RGB formats. > > */ > > info = vsp1_get_format_info(video->vsp1, pix->pixelformat); > > - if (info == NULL) > > - info = vsp1_get_format_info(video->vsp1, VSP1_VIDEO_DEF_FORMAT); > > + if (!info || (video->rwpf->has_writeback && !vsp1_format_is_rgb(info))) > > + info = vsp1_get_format_info(video->vsp1, > > + vsp1_video_default_format(video)); > > > > pix->pixelformat = info->fourcc; > > pix->colorspace = V4L2_COLORSPACE_SRGB; > > @@ -946,6 +955,122 @@ static const struct vb2_ops vsp1_video_queue_qops = { > > .stop_streaming = vsp1_video_stop_streaming, > > }; > > > > +/* ----------------------------------------------------------------------------- > > + * Writeback Support > > + */ > > + > > +static void vsp1_video_wb_buffer_queue(struct vb2_buffer *vb) > > +{ > > + struct vb2_v4l2_buffer *vbuf = to_vb2_v4l2_buffer(vb); > > + struct vsp1_video *video = vb2_get_drv_priv(vb->vb2_queue); > > + struct vsp1_vb2_buffer *buf = to_vsp1_vb2_buffer(vbuf); > > + unsigned long flags; > > + > > + spin_lock_irqsave(&video->irqlock, flags); > > + list_add_tail(&buf->queue, &video->irqqueue); > > + spin_unlock_irqrestore(&video->irqlock, flags); > > +} > > + > > +static int vsp1_video_wb_start_streaming(struct vb2_queue *vq, > > + unsigned int count) > > +{ > > + struct vsp1_video *video = vb2_get_drv_priv(vq); > > + > > + video->wb_running = true; > > + return 0; > > +} > > + > > +static bool vsp1_video_wb_stopped(struct vsp1_video *video) > > +{ > > + unsigned long flags; > > + bool stopped; > > + > > + spin_lock_irqsave(&video->irqlock, flags); > > + stopped = list_empty(&video->wb_queue); > > + spin_unlock_irqrestore(&video->irqlock, flags); > > + > > + return stopped; > > +} > > + > > +static void vsp1_video_wb_stop_streaming(struct vb2_queue *vq) > > +{ > > + struct vsp1_video *video = vb2_get_drv_priv(vq); > > + struct vsp1_rwpf *rwpf = video->rwpf; > > + struct vsp1_pipeline *pipe = rwpf->entity.pipe; > > + unsigned long flags; > > + int ret; > > + > > + /* Disable writeback and wait for the pending frames to complete. */ > > + spin_lock_irqsave(&video->irqlock, flags); > > + video->wb_running = false; > > + spin_unlock_irqrestore(&video->irqlock, flags); > > + > > + ret = wait_event_timeout(pipe->wq, vsp1_video_wb_stopped(video), > > + msecs_to_jiffies(500)); > > + if (ret == 0) { > > + dev_err(video->vsp1->dev, "writeback stop timeout\n"); > > + list_splice_init(&video->wb_queue, &video->irqqueue); > > + } > > + > > + vsp1_video_release_buffers(video); > > +} > > + > > +static const struct vb2_ops vsp1_video_wb_queue_qops = { > > + .queue_setup = vsp1_video_queue_setup, > > + .buf_prepare = vsp1_video_buffer_prepare, > > + .buf_queue = vsp1_video_wb_buffer_queue, > > + .wait_prepare = vb2_ops_wait_prepare, > > + .wait_finish = vb2_ops_wait_finish, > > + .start_streaming = vsp1_video_wb_start_streaming, > > + .stop_streaming = vsp1_video_wb_stop_streaming, > > +}; > > + > > +void vsp1_video_wb_prepare(struct vsp1_video *video) > > +{ > > + struct vsp1_vb2_buffer *buf; > > + unsigned long flags; > > + > > + /* > > + * If writeback is disabled, return immediately. Otherwise remove the > > + * first buffer from the irqqueue, add it to the writeback queue and > > + * configure the WPF for writeback. > > + */ > > + > > + spin_lock_irqsave(&video->irqlock, flags); > > + > > + if (!video->wb_running) { > > + spin_unlock_irqrestore(&video->irqlock, flags); > > + return; > > + } > > + > > + buf = list_first_entry_or_null(&video->irqqueue, struct vsp1_vb2_buffer, > > + queue); > > + if (buf) > > + list_move_tail(&buf->queue, &video->wb_queue); > > + > > + spin_unlock_irqrestore(&video->irqlock, flags); > > + > > + if (buf) { > > + video->rwpf->mem = buf->mem; > > + video->rwpf->writeback = true; > > + } > > +} > > + > > +void vsp1_video_wb_frame_end(struct vsp1_video *video) > > +{ > > + struct vsp1_vb2_buffer *done; > > + unsigned long flags; > > + > > + /* Complete the first buffer from the writeback queue. */ > > + spin_lock_irqsave(&video->irqlock, flags); > > + done = list_first_entry(&video->wb_queue, struct vsp1_vb2_buffer, > > + queue); > > + list_del(&done->queue); > > + spin_unlock_irqrestore(&video->irqlock, flags); > > + > > + vsp1_video_complete_buffer(video, done); > > +} > > + > > /* ----------------------------------------------------------------------------- > > * V4L2 ioctls > > */ > > @@ -1045,6 +1170,13 @@ vsp1_video_streamon(struct file *file, void *fh, enum v4l2_buf_type type) > > if (video->queue.owner && video->queue.owner != file->private_data) > > return -EBUSY; > > > > + /* > > + * Writeback video devices don't need to interface with the pipeline or > > + * verify formats, just turn streaming on. > > + */ > > + if (video->rwpf->has_writeback) > > + return vb2_streamon(&video->queue, type); > > + > > /* > > * Get a pipeline for the video node and start streaming on it. No link > > * touching an entity in the pipeline can be activated or deactivated > > @@ -1273,7 +1405,7 @@ struct vsp1_video *vsp1_video_create(struct vsp1_device *vsp1, > > video->pad.flags = MEDIA_PAD_FL_SOURCE; > > video->video.vfl_dir = VFL_DIR_TX; > > } else { > > - direction = "output"; > > + direction = rwpf->has_writeback ? "writeback" : "output"; > > video->type = V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE; > > video->pad.flags = MEDIA_PAD_FL_SINK; > > video->video.vfl_dir = VFL_DIR_RX; > > @@ -1282,6 +1414,7 @@ struct vsp1_video *vsp1_video_create(struct vsp1_device *vsp1, > > mutex_init(&video->lock); > > spin_lock_init(&video->irqlock); > > INIT_LIST_HEAD(&video->irqqueue); > > + INIT_LIST_HEAD(&video->wb_queue); > > > > /* Initialize the media entity... */ > > ret = media_entity_pads_init(&video->video.entity, 1, &video->pad); > > @@ -1289,7 +1422,7 @@ struct vsp1_video *vsp1_video_create(struct vsp1_device *vsp1, > > return ERR_PTR(ret); > > > > /* ... and the format ... */ > > - rwpf->format.pixelformat = VSP1_VIDEO_DEF_FORMAT; > > + rwpf->format.pixelformat = vsp1_video_default_format(video); > > rwpf->format.width = VSP1_VIDEO_DEF_WIDTH; > > rwpf->format.height = VSP1_VIDEO_DEF_HEIGHT; > > __vsp1_video_try_format(video, &rwpf->format, &rwpf->fmtinfo); > > @@ -1310,7 +1443,10 @@ struct vsp1_video *vsp1_video_create(struct vsp1_device *vsp1, > > video->queue.lock = &video->lock; > > video->queue.drv_priv = video; > > video->queue.buf_struct_size = sizeof(struct vsp1_vb2_buffer); > > - video->queue.ops = &vsp1_video_queue_qops; > > + if (rwpf->has_writeback) > > + video->queue.ops = &vsp1_video_wb_queue_qops; > > + else > > + video->queue.ops = &vsp1_video_queue_qops; > > video->queue.mem_ops = &vb2_dma_contig_memops; > > video->queue.timestamp_flags = V4L2_BUF_FLAG_TIMESTAMP_COPY; > > video->queue.dev = video->vsp1->bus_master; > > diff --git a/drivers/media/platform/vsp1/vsp1_video.h b/drivers/media/platform/vsp1/vsp1_video.h > > index f3cf5e2fdf5a..13b357b07ee2 100644 > > --- a/drivers/media/platform/vsp1/vsp1_video.h > > +++ b/drivers/media/platform/vsp1/vsp1_video.h > > @@ -44,6 +44,9 @@ struct vsp1_video { > > struct vb2_queue queue; > > spinlock_t irqlock; > > struct list_head irqqueue; > > + > > + bool wb_running; > > + struct list_head wb_queue; > > }; > > > > static inline struct vsp1_video *to_vsp1_video(struct video_device *vdev) > > @@ -54,6 +57,9 @@ static inline struct vsp1_video *to_vsp1_video(struct video_device *vdev) > > void vsp1_video_suspend(struct vsp1_device *vsp1); > > void vsp1_video_resume(struct vsp1_device *vsp1); > > > > +void vsp1_video_wb_prepare(struct vsp1_video *video); > > +void vsp1_video_wb_frame_end(struct vsp1_video *video); > > + > > struct vsp1_video *vsp1_video_create(struct vsp1_device *vsp1, > > struct vsp1_rwpf *rwpf); > > void vsp1_video_cleanup(struct vsp1_video *video); > > diff --git a/drivers/media/platform/vsp1/vsp1_wpf.c b/drivers/media/platform/vsp1/vsp1_wpf.c > > index 18c49e3a7875..81650a625185 100644 > > --- a/drivers/media/platform/vsp1/vsp1_wpf.c > > +++ b/drivers/media/platform/vsp1/vsp1_wpf.c > > @@ -240,6 +240,7 @@ static void wpf_configure_stream(struct vsp1_entity *entity, > > struct vsp1_device *vsp1 = wpf->entity.vsp1; > > const struct v4l2_mbus_framefmt *source_format; > > const struct v4l2_mbus_framefmt *sink_format; > > + unsigned int index = wpf->entity.index; > > unsigned int i; > > u32 outfmt = 0; > > u32 srcrpf = 0; > > @@ -250,8 +251,9 @@ static void wpf_configure_stream(struct vsp1_entity *entity, > > source_format = vsp1_entity_get_pad_format(&wpf->entity, > > wpf->entity.config, > > RWPF_PAD_SOURCE); > > + > > /* Format */ > > - if (!pipe->lif) { > > + if (!pipe->lif || wpf->writeback) { > > const struct v4l2_pix_format_mplane *format = &wpf->format; > > const struct vsp1_format_info *fmtinfo = wpf->fmtinfo; > > > > @@ -276,8 +278,7 @@ static void wpf_configure_stream(struct vsp1_entity *entity, > > > > vsp1_wpf_write(wpf, dlb, VI6_WPF_DSWAP, fmtinfo->swap); > > > > - if (vsp1_feature(vsp1, VSP1_HAS_WPF_HFLIP) && > > - wpf->entity.index == 0) > > + if (vsp1_feature(vsp1, VSP1_HAS_WPF_HFLIP) && index == 0) > > vsp1_wpf_write(wpf, dlb, VI6_WPF_ROT_CTRL, > > VI6_WPF_ROT_CTRL_LN16 | > > (256 << VI6_WPF_ROT_CTRL_LMEM_WD_SHIFT)); > > @@ -288,11 +289,9 @@ static void wpf_configure_stream(struct vsp1_entity *entity, > > > > wpf->outfmt = outfmt; > > > > - vsp1_dl_body_write(dlb, VI6_DPR_WPF_FPORCH(wpf->entity.index), > > + vsp1_dl_body_write(dlb, VI6_DPR_WPF_FPORCH(index), > > VI6_DPR_WPF_FPORCH_FP_WPFN); > > > > - vsp1_dl_body_write(dlb, VI6_WPF_WRBCK_CTRL(wpf->entity.index), 0); > > - > > /* > > * Sources. If the pipeline has a single input and BRx is not used, > > * configure it as the master layer. Otherwise configure all > > @@ -318,9 +317,24 @@ static void wpf_configure_stream(struct vsp1_entity *entity, > > vsp1_wpf_write(wpf, dlb, VI6_WPF_SRCRPF, srcrpf); > > > > /* Enable interrupts. */ > > - vsp1_dl_body_write(dlb, VI6_WPF_IRQ_STA(wpf->entity.index), 0); > > - vsp1_dl_body_write(dlb, VI6_WPF_IRQ_ENB(wpf->entity.index), > > + vsp1_dl_body_write(dlb, VI6_WPF_IRQ_STA(index), 0); > > + vsp1_dl_body_write(dlb, VI6_WPF_IRQ_ENB(index), > > VI6_WFP_IRQ_ENB_DFEE); > > + > > + /* > > + * Configure writeback for display pipelines. The wpf writeback flag is > > + * never set for memory-to-memory pipelines. > > + */ > > + vsp1_dl_body_write(dlb, VI6_DISP_IRQ_STA(index), 0); > > + if (wpf->writeback) { > > I feel like a comment here would be useful to make it clear that by > using _patch the VI6_DISP_IRQ_ENB_DSTE, and VI6_WPF_WRBCK_CTRL_WBMD will > be reset to 0 at the frame-end? > > But maybe that's too verbose ... and won't be an issue once the function > documentation is updated for vsp1_dl_body_write_patch(). I'll add a comment. > > + vsp1_dl_body_write_patch(dlb, VI6_DISP_IRQ_ENB(index), > > + VI6_DISP_IRQ_ENB_DSTE, 0); > > + vsp1_dl_body_write_patch(dlb, VI6_WPF_WRBCK_CTRL(index), > > + VI6_WPF_WRBCK_CTRL_WBMD, 0); > > + } else { > > + vsp1_dl_body_write(dlb, VI6_DISP_IRQ_ENB(index), 0); > > + vsp1_dl_body_write(dlb, VI6_WPF_WRBCK_CTRL(index), 0); > > + } > > } > > > > static void wpf_configure_frame(struct vsp1_entity *entity, > > @@ -390,7 +404,11 @@ static void wpf_configure_partition(struct vsp1_entity *entity, > > (0 << VI6_WPF_SZCLIP_OFST_SHIFT) | > > (height << VI6_WPF_SZCLIP_SIZE_SHIFT)); > > > > - if (pipe->lif) > > + /* > > + * For display pipelines without writeback enabled there's no memory > > + * address to configure, return now. > > + */ > > + if (pipe->lif && !wpf->writeback) > > return; > > > > /* > > @@ -479,6 +497,12 @@ static void wpf_configure_partition(struct vsp1_entity *entity, > > vsp1_wpf_write(wpf, dlb, VI6_WPF_DSTM_ADDR_Y, mem.addr[0]); > > vsp1_wpf_write(wpf, dlb, VI6_WPF_DSTM_ADDR_C0, mem.addr[1]); > > vsp1_wpf_write(wpf, dlb, VI6_WPF_DSTM_ADDR_C1, mem.addr[2]); > > + > > + /* > > + * Writeback operates in single-shot mode and lasts for a single frame, > > + * reset the writeback flag to false for the next frame. > > + */ > > + wpf->writeback = false; > > This differs from my implementation right? I think my version just ran > whenever there was a buffer available. (Except that when there was no > atomic_flush - there was a large amount of latency...) Yes, it differs quite a bit. > I guess this comes down to the fact that we will not queue up frames > except unless there is a real frame-change caused by a fresh > atomic_flush ... and so the buffer rate does not reflect the display > refresh rate. You can queue buffers at any time but they will only be processed on an atomic commit. > Now that I've written the above, I think that's made the reasoning > clearer for me so I've answered my own questions :) > > > } > > > > static unsigned int wpf_max_width(struct vsp1_entity *entity, > > @@ -529,6 +553,13 @@ struct vsp1_rwpf *vsp1_wpf_create(struct vsp1_device *vsp1, unsigned int index) > > wpf->max_height = WPF_GEN3_MAX_HEIGHT; > > } > > > > + /* > > + * On Gen3 WPFs with a LIF output can also write to memory for display > > Hrm ... I might have said 'with an LIF'. ... but it depends whether you say: > 'with a liph' > > or you spell it out: > > 'with an ell-eye-eff > > I personally spell out acronyms in my head, so that makes is 'an'. I do it the other way :-) > It doesn't matter which really here though :-) > > > + * writeback. > > + */ > > + if (vsp1->info->gen > 2 && index < vsp1->info->lif_count) > > + wpf->has_writeback = true; > > + > > wpf->entity.ops = &wpf_entity_ops; > > wpf->entity.type = VSP1_ENTITY_WPF; > > wpf->entity.index = index; -- Regards, Laurent Pinchart From mboxrd@z Thu Jan 1 00:00:00 1970 From: Laurent Pinchart Subject: Re: [PATCH v4 7/7] media: vsp1: Provide a writeback video device Date: Tue, 19 Feb 2019 02:31:26 +0200 Message-ID: <20190219003126.GE5082@pendragon.ideasonboard.com> References: <20190217024852.23328-1-laurent.pinchart+renesas@ideasonboard.com> <20190217024852.23328-8-laurent.pinchart+renesas@ideasonboard.com> <42e86cc1-ff3d-1e98-9da6-b072497dbed2@ideasonboard.com> Mime-Version: 1.0 Content-Type: text/plain; charset="utf-8" Content-Transfer-Encoding: base64 Return-path: Received: from perceval.ideasonboard.com (perceval.ideasonboard.com [213.167.242.64]) by gabe.freedesktop.org (Postfix) with ESMTPS id 0AD4C8903B for ; Tue, 19 Feb 2019 00:31:33 +0000 (UTC) Content-Disposition: inline In-Reply-To: <42e86cc1-ff3d-1e98-9da6-b072497dbed2@ideasonboard.com> List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: dri-devel-bounces@lists.freedesktop.org Sender: "dri-devel" To: Kieran Bingham Cc: Laurent Pinchart , dri-devel@lists.freedesktop.org, linux-media@vger.kernel.org List-Id: dri-devel@lists.freedesktop.org SGkgS2llcmFuLAoKT24gU3VuLCBGZWIgMTcsIDIwMTkgYXQgMDg6MDY6MzJQTSArMDAwMCwgS2ll cmFuIEJpbmdoYW0gd3JvdGU6Cj4gT24gMTcvMDIvMjAxOSAwMjo0OCwgTGF1cmVudCBQaW5jaGFy dCB3cm90ZToKPiA+IEZyb206IEtpZXJhbiBCaW5naGFtIDxraWVyYW4uYmluZ2hhbStyZW5lc2Fz QGlkZWFzb25ib2FyZC5jb20+Cj4gPiAKPiA+IFdoZW4gdGhlIFZTUDEgaXMgdXNlZCBpbiBhbiBh Y3RpdmUgZGlzcGxheSBwaXBlbGluZSwgdGhlIG91dHB1dCBvZiB0aGUKPiA+IFdQRiBjYW4gc3Vw cGx5IHRoZSBMSUYgZW50aXR5IGRpcmVjdGx5IGFuZCBzaW11bHRhbmVvdXNseSB3cml0ZSB0bwo+ ID4gbWVtb3J5Lgo+ID4gCj4gPiBTdXBwb3J0IHRoaXMgZnVuY3Rpb25hbGl0eSBpbiB0aGUgVlNQ MSBkcml2ZXIgdGhyb3VnaCBhIFY0TDIgdmlkZW8KPiA+IGRldmljZSBub2RlIGNvbm5lY3RlZCB0 byB0aGUgV1BGLgo+ID4gCj4gPiBUaGUgd3JpdGViYWNrIHZpZGVvIG5vZGUgc3VwcG9ydCBSR0Ig Zm9ybWF0cyBvbmx5IGR1ZSB0byB0aGUgV1BGCj4gPiBvdXRwdXR0aW5nIFJHQiB0byB0aGUgTElG LiBUaGUgcGl4ZWwgZm9ybWF0IGNhbiBvdGhlcndpc2UgYmUgY29uZmlndXJlZAo+ID4gZnJlZWx5 Lgo+ID4gCj4gPiBUaGUgcmVzb2x1dGlvbiBvZiB0aGUgY2FwdHVyZWQgZnJhbWVzIGFyZSBzZXQg YnkgdGhlIGRpc3BsYXkgbW9kZS4gQQo+ID4gZGlmZmVyZW50IHJlc29sdXRpb24gY2FuIGJlIHNl bGVjdGVkIG9uIHRoZSB2aWRlbyBub2RlLCBpbiB3aGljaCBjYXNlCj4gPiBjcm9wcGluZyBvciBj b21wb3Npbmcgd2lsbCBiZSBwZXJmb3JtZWQuCj4gPiAKPiA+IFNpZ25lZC1vZmYtYnk6IEtpZXJh biBCaW5naGFtIDxraWVyYW4uYmluZ2hhbStyZW5lc2FzQGlkZWFzb25ib2FyZC5jb20+Cj4gPiBT aWduZWQtb2ZmLWJ5OiBMYXVyZW50IFBpbmNoYXJ0IDxsYXVyZW50LnBpbmNoYXJ0K3JlbmVzYXNA aWRlYXNvbmJvYXJkLmNvbT4KPiAKPiBGb3IgeW91ciBjaGFuZ2VzLAo+IAo+IFdpdGggdGhlIGRv Y3VtZW50YXRpb24gdXBkYXRlZCBmb3IgdnNwMV9kbF9ib2R5X3dyaXRlX3BhdGNoKCksCj4gCj4g UmV2aWV3ZWQtYnk6IEtpZXJhbiBCaW5naGFtIDxraWVyYW4uYmluZ2hhbStyZW5lc2FzQGlkZWFz b25ib2FyZC5jb20+Cj4gCj4gPiAtLS0KPiA+IENoYW5nZXMgc2luY2UgdjM6Cj4gPiAKPiA+IC0g SW5mZXIgaGFzX3dyaXRlYmFjayBmcm9tIHRoZSBudW1iZXIgb2YgTElGcyBhbmQgdGhlIGdlbmVy YXRpb24KPiA+IC0gUmVtb3ZlIHZzcDFfdmlkZW86OmlzX3dyaXRlYmFjawo+ID4gLSBEZXNjcmli ZSB3cml0ZWJhY2sgdmlkZW8gbm9kZXMgYXMgJ3dyaXRlYmFjaycKPiA+IC0gQWRkIG1lY2hhbmlz bSB0byBwYXRjaCBhY3RpdmUgZGlzcGxheSBsaXN0cwo+ID4gLSBIYW5kbGUgd3JpdGViYWNrIGZv cm1hdCByZXN0cmljdGlvbnMKPiA+IC0gRG9uJ3Qgd2FpdCBmb3IgbmV4dCBwYWdlIGZsaXAgYmVm b3JlIGNvbXBsZXRpbmcgd3JpdGViYWNrIGJ1ZmZlcgo+IAo+IFRoaXMgaXMgYSBuaWNlIGFkZGl0 aW9uLgoKVGhhbmsgeW91LiBJdCB3YXMgdGhlIGhhcmQgcGFydCA6KQoKPiA+IC0gUGVyaW9kcyBh dCB0aGUgZW5kIG9mIHNlbnRlbmNlcy4KPiAKPiBZb3UgYWxzbyBmaXggd3JpdGViYWNrIGZvciB0 aGUgYml0cm90IHRoYXQgdGhlIHByZXZpb3VzIHNldHMgaGFkIG5vdwo+IHRoYXQgd2UgaGF2ZSBw YXJ0aXRpb24gaGFuZGxpbmcuCj4gCj4gSW50ZXJlc3RpbmdseSBteSBsb2NhbCBpbXBsZW1lbnRh dGlvbiBmb3IgdGhpcyBiaXRyb3Qgd2FzIGp1c3QgdG8KPiBhbGxvY2F0ZSBhIHRhYmxlIGZvciBh IHNpbmdsZSBwYXJ0aXRpb24uIEkgbGlrZSB5b3VyIGltcGxlbWVudGF0aW9uCj4gYmV0dGVyIDop CgpUaGFuayB5b3UuCgo+ID4gQ2hhbmdlcyBzaW5jZSB2MjoKPiA+ICAtIFJlYmFzZWQgdG8gdjQu MTItcmMxCj4gPiAKPiA+IENoYW5nZXMgc2luY2UgUkZDCj4gPiAgLSBGaXggY2hlY2twYXRjaC5w bCB3YXJuaW5ncwo+ID4gIC0gQWRhcHQgdG8gdXNlIGEgc2luZ2xlIHNvdXJjZSBwYWQgZm9yIHRo ZSBXcml0ZWJhY2sgYW5kIExJRgo+ID4gIC0gVXNlIFdQRiBwcm9wZXJ0aWVzIHRvIGRldGVybWlu ZSB3aGVuIHRvIGNyZWF0ZSBsaW5rcyBpbnN0ZWFkIG9mIFZTUAo+ID4gIC0gUmVtb3ZlIGluY29y cmVjdCB2c3AxX3ZpZGVvX3ZlcmlmeV9mb3JtYXQoKSBjaGFuZ2VzCj4gPiAgLSBTcGVsbGluZyBh bmQgZ3JhbW1hciBmaXhlcwo+ID4gLS0tCj4gPiAgZHJpdmVycy9tZWRpYS9wbGF0Zm9ybS92c3Ax L3ZzcDFfZGwuYyAgICB8ICA4MyArKysrKysrKysrKysrCj4gPiAgZHJpdmVycy9tZWRpYS9wbGF0 Zm9ybS92c3AxL3ZzcDFfZGwuaCAgICB8ICAgNCArCj4gPiAgZHJpdmVycy9tZWRpYS9wbGF0Zm9y bS92c3AxL3ZzcDFfZHJtLmMgICB8ICAxNCArKy0KPiA+ICBkcml2ZXJzL21lZGlhL3BsYXRmb3Jt L3ZzcDEvdnNwMV9kcnYuYyAgIHwgIDE3ICsrLQo+ID4gIGRyaXZlcnMvbWVkaWEvcGxhdGZvcm0v dnNwMS92c3AxX3BpcGUuYyAgfCAgIDUgKwo+ID4gIGRyaXZlcnMvbWVkaWEvcGxhdGZvcm0vdnNw MS92c3AxX3BpcGUuaCAgfCAgIDYgKwo+ID4gIGRyaXZlcnMvbWVkaWEvcGxhdGZvcm0vdnNwMS92 c3AxX3J3cGYuaCAgfCAgIDIgKwo+ID4gIGRyaXZlcnMvbWVkaWEvcGxhdGZvcm0vdnNwMS92c3Ax X3ZpZGVvLmMgfCAxNTAgKysrKysrKysrKysrKysrKysrKysrLS0KPiA+ICBkcml2ZXJzL21lZGlh L3BsYXRmb3JtL3ZzcDEvdnNwMV92aWRlby5oIHwgICA2ICsKPiA+ICBkcml2ZXJzL21lZGlhL3Bs YXRmb3JtL3ZzcDEvdnNwMV93cGYuYyAgIHwgIDQ5ICsrKysrKy0tCj4gPiAgMTAgZmlsZXMgY2hh bmdlZCwgMzE4IGluc2VydGlvbnMoKyksIDE4IGRlbGV0aW9ucygtKQo+ID4gCj4gPiBkaWZmIC0t Z2l0IGEvZHJpdmVycy9tZWRpYS9wbGF0Zm9ybS92c3AxL3ZzcDFfZGwuYyBiL2RyaXZlcnMvbWVk aWEvcGxhdGZvcm0vdnNwMS92c3AxX2RsLmMKPiA+IGluZGV4IDg4NmIzYTY5ZDMyOS4uNTkxNTQ0 MzgyOTQ2IDEwMDY0NAo+ID4gLS0tIGEvZHJpdmVycy9tZWRpYS9wbGF0Zm9ybS92c3AxL3ZzcDFf ZGwuYwo+ID4gKysrIGIvZHJpdmVycy9tZWRpYS9wbGF0Zm9ybS92c3AxL3ZzcDFfZGwuYwo+ID4g QEAgLTExNSw2ICsxMTUsMTIgQEAgc3RydWN0IHZzcDFfZGxfYm9keSB7Cj4gPiAgCj4gPiAgCXVu c2lnbmVkIGludCBudW1fZW50cmllczsKPiA+ICAJdW5zaWduZWQgaW50IG1heF9lbnRyaWVzOwo+ ID4gKwo+ID4gKwl1bnNpZ25lZCBpbnQgbnVtX3BhdGNoZXM7Cj4gPiArCXN0cnVjdCB7Cj4gPiAr CQlzdHJ1Y3QgdnNwMV9kbF9lbnRyeSAqZW50cnk7Cj4gPiArCQl1MzIgZGF0YTsKPiA+ICsJfSBw YXRjaGVzWzJdOwo+IAo+IFdoYXQncyB0aGUgc2lnbmlmaWNhbmNlIG9mIFsyXSA/Cj4gUGVyaGFw cyBpdCB3aWxsIGJlIGNsZWFyIHdoYXQgdHdvIGVudHJ5J3Mgc3VwcG9ydCBwYXRjaGluZyBsYXRl ci4uLgo+IAo+IE9rIC0geWVzIC0gaXQncyB0byBwYXRjaCBib3RoIHRoZSBXcml0ZWJhY2sgZW5h YmxlIGFuZCB0aGUgZGlzcGxheSBzdGFydAo+IGVuYWJsZS4KClllcywgd2Ugb25seSBuZWVkIHR3 byByZWdpc3RlcnMuIFRoaXMgaXMgYSBiaXQgb2YgYSBoYWNrLCBJJ2QgbGlrZSB0bwpjb21lIHVw IHdpdGggYSBiZXR0ZXIgQVBJLCBidXQgbWFraW5nIGl0IGdlbmVyaWMgd2lsbCBiZSB1bm5lZWRp bmdseQpjb3N0bHkuCgo+ID4gIH07Cj4gPiAgCj4gPiAgLyoqCj4gPiBAQCAtMzYxLDYgKzM2Nyw3 IEBAIHZvaWQgdnNwMV9kbF9ib2R5X3B1dChzdHJ1Y3QgdnNwMV9kbF9ib2R5ICpkbGIpCj4gPiAg CQlyZXR1cm47Cj4gPiAgCj4gPiAgCWRsYi0+bnVtX2VudHJpZXMgPSAwOwo+ID4gKwlkbGItPm51 bV9wYXRjaGVzID0gMDsKPiA+ICAKPiA+ICAJc3Bpbl9sb2NrX2lycXNhdmUoJmRsYi0+cG9vbC0+ bG9jaywgZmxhZ3MpOwo+ID4gIAlsaXN0X2FkZF90YWlsKCZkbGItPmZyZWUsICZkbGItPnBvb2wt PmZyZWUpOwo+ID4gQEAgLTM4OCw2ICszOTUsMzcgQEAgdm9pZCB2c3AxX2RsX2JvZHlfd3JpdGUo c3RydWN0IHZzcDFfZGxfYm9keSAqZGxiLCB1MzIgcmVnLCB1MzIgZGF0YSkKPiA+ICAJZGxiLT5u dW1fZW50cmllcysrOwo+ID4gIH0KPiA+ICAKPiA+ICsvKioKPiA+ICsgKiB2c3AxX2RsX2JvZHlf d3JpdGUgLSBXcml0ZSBhIHJlZ2lzdGVyIHRvIGEgZGlzcGxheSBsaXN0IGJvZHkKPiAKPiBzL193 cml0ZS9fd3JpdGVfcGF0Y2gvCgpPb3BzLiBJIGZvcmdvdCB0byB1cGRhdGUgdGhlIGRvY3VtZW50 YXRpb24gOi0vCgo+ICJTdG9yZSBhbiB1cGRhdGUgdG8gYW4gZXhpc3RpbmcgcmVnaXN0ZXIgZm9y IGhhbmRsaW5nIGF0IGRpc3BsYXktc3RhcnQKPiBpbnRlcnJ1cHQuLi4uIj8gKG9yIGFzIHlvdSBz ZWUgZml0KQoKVGhlIGZ1bmN0aW9uIHdyaXRlcyBhIHJlZ2lzdGVyIGFuZCBzdG9yZXMgdGhlIHVw ZGF0ZS4gSSdsbCBmaXggdGhlCmRvY3VtZW50YXRpb24uCgovKioKICogdnNwMV9kbF9ib2R5X3dy aXRlX3BhdGNoIC0gV3JpdGUgYSByZWdpc3RlciB0byBhIGRpc3BsYXkgbGlzdCBib2R5IHdpdGgg YW4KICogICAgICB1cGRhdGUgZm9yIHRoZSBuZXh0IHZibGFuawogKiBAZGxiOiBUaGUgYm9keQog KiBAcmVnOiBUaGUgcmVnaXN0ZXIgYWRkcmVzcwogKiBAZGF0YTogVGhlIHJlZ2lzdGVyIHZhbHVl CiAqIEBwYXRjaDogVGhlIHJlZ2lzdGVyIHZhbHVlIGZvciB0aGUgbmV4dCB2YmxhbmsKICoKICog RGlzcGxheSBsaXN0cyBpbiBjb250aW51b3VzIG1vZGUgYXJlIHJlLXVzZWQgYnkgdGhlIGhhcmR3 YXJlIGZvciBzdWNjZXNzaXZlCiAqIGZyYW1lcyB1bnRpbCBhIG5ldyBkaXNwbGF5IGxpc3QgaXMg Y29tbWl0dGVkLiBDaGFuZ2luZyB0aGUgVlNQIGNvbmZpZ3VyYXRpb24KICogbm9ybWFsbHkgcmVx dWlyZXMgY3JlYXRpbmcgYW5kIGNvbW1pdHRpbmcgYSBuZXcgZGlzcGxheSBsaXN0LiBUaGlzIGZ1 bmN0aW9uCiAqIG9mZmVycyBhbiBhbHRlcm5hdGl2ZSByYWNlLWZyZWUgd2F5IGJ5IHdyaXRpbmcg YSBAdmFsdWUgdG8gdGhlIEByZWdpc3RlciBpbgogKiB0aGUgZGlzcGxheSBsaXN0IGJvZHksIGFs b25nIHdpdGggYW4gdXBkYXRlZCBAcGF0Y2ggdmFsdWUgdG8gYmUgd3JpdHRlbiB0bwogKiB0aGUg VlNQIG9uZSB2YmxhbmsgYWZ0ZXIgdGhlIGRpc3BsYXkgbGlzdCBpcyBjb21taXR0ZWQuCiAqCiAq IFRoZSBtYXhpbXVtIG51bWJlciBvZiBwYXRjaCBlbnRyaWVzIHRoYXQgY2FuIGJlIHdyaXR0ZW4g aW4gYSBib2R5IGlzIDIuCiAqLwoKPiA+ICsgKiBAZGxiOiBUaGUgYm9keQo+ID4gKyAqIEByZWc6 IFRoZSByZWdpc3RlciBhZGRyZXNzCj4gPiArICogQGRhdGE6IFRoZSByZWdpc3RlciB2YWx1ZQo+ ID4gKyAqCj4gCj4gKyBwYXRjaDogVGhlIHVwZGF0ZWQgdmFsdWUgdG8gbW9kaWZ5Li4uCj4gCj4g PiArICogV3JpdGUgdGhlIGdpdmVuIHJlZ2lzdGVyIGFuZCB2YWx1ZSB0byB0aGUgZGlzcGxheSBs aXN0IGJvZHkuIFRoZSBtYXhpbXVtCj4gPiArICogbnVtYmVyIG9mIGVudHJpZXMgdGhhdCBjYW4g YmUgd3JpdHRlbiBpbiBhIGJvZHkgaXMgc3BlY2lmaWVkIHdoZW4gdGhlIGJvZHkgaXMKPiA+ICsg KiBhbGxvY2F0ZWQgYnkgdnNwMV9kbF9ib2R5X2FsbG9jKCkuCj4gCj4gSSBndWVzcyB0aGlzIGlz IGEgY29weS9wYXN0ZSBoYW5nb3Zlci4KPiAKPiBIb3cgYWJvdXQ6Cj4gCj4gIkRpc3BsYXkgbGlz dHMgaW4gY29udGludW91cyBtb2RlIGFyZSByZS11c2VkIGJ5IHRoZSBoYXJkd2FyZSBmb3IKPiBz dWNjZXNzaXZlIGZyYW1lcyB3aXRob3V0IG5lZWRlZCB0byByZWNvbW1pdCBhIG5ldyBkaXNwbGF5 IGxpc3QuIEEgcGF0Y2gKPiBhbGxvd3MgdXMgdG8gYXBwbHkgc21hbGwgY2hhbmdlcyB0byB0aGUg ZGlzcGxheSBsaXN0IGJlZm9yZSBpdCBpcyByZXVzZWQKPiB0byBhbGxvdyBtaW5vciBjb25maWd1 cmF0aW9uIGNoYW5nZXMgd2l0aG91dCBpbnZvbHZpbmcgYSBmdWxsIHJld3JpdGUgb2YKPiB0aGUg bGlzdCBvciBmYWNpbmcgYSByYWNlIGF0IGNvbW1pdC4iCj4gCj4gKE9yIGhvd2V2ZXIgeW91IHNl ZSBmaXQuLi4pCj4gCj4gPiArICovCj4gPiArdm9pZCB2c3AxX2RsX2JvZHlfd3JpdGVfcGF0Y2go c3RydWN0IHZzcDFfZGxfYm9keSAqZGxiLCB1MzIgcmVnLCB1MzIgZGF0YSwKPiA+ICsJCQkgICAg ICB1MzIgcGF0Y2gpCj4gPiArewo+ID4gKwlpZiAoV0FSTl9PTkNFKGRsYi0+bnVtX2VudHJpZXMg Pj0gZGxiLT5tYXhfZW50cmllcywKPiA+ICsJCSAgICAgICJETEIgc2l6ZSBleGNlZWRlZCAobWF4 ICV1KSIsIGRsYi0+bWF4X2VudHJpZXMpKQo+ID4gKwkJcmV0dXJuOwo+ID4gKwo+ID4gKwlpZiAo V0FSTl9PTkNFKGRsYi0+bnVtX3BhdGNoZXMgPj0gQVJSQVlfU0laRShkbGItPnBhdGNoZXMpLAo+ ID4gKwkJICAgICAgIkRMQiBwYXRjaGVzIHNpemUgZXhjZWVkZWQgKG1heCAlbHUpIiwKPiA+ICsJ CSAgICAgIEFSUkFZX1NJWkUoZGxiLT5wYXRjaGVzKSkpCj4gPiArCQlyZXR1cm47Cj4gPiArCj4g PiArCWRsYi0+cGF0Y2hlc1tkbGItPm51bV9wYXRjaGVzXS5lbnRyeSA9ICZkbGItPmVudHJpZXNb ZGxiLT5udW1fZW50cmllc107Cj4gPiArCWRsYi0+cGF0Y2hlc1tkbGItPm51bV9wYXRjaGVzXS5k YXRhID0gcGF0Y2g7Cj4gPiArCWRsYi0+bnVtX3BhdGNoZXMrKzsKPiA+ICsKPiA+ICsJZGxiLT5l bnRyaWVzW2RsYi0+bnVtX2VudHJpZXNdLmFkZHIgPSByZWc7Cj4gPiArCWRsYi0+ZW50cmllc1tk bGItPm51bV9lbnRyaWVzXS5kYXRhID0gZGF0YTsKPiA+ICsJZGxiLT5udW1fZW50cmllcysrOwo+ ID4gK30KPiA+ICsKPiA+ICAvKiAtLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0t LS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLQo+ID4gICAqIERpc3BsYXkg TGlzdCBFeHRlbmRlZCBDb21tYW5kIE1hbmFnZW1lbnQKPiA+ICAgKi8KPiA+IEBAIC02NTIsNiAr NjkwLDcgQEAgc3RhdGljIHZvaWQgX192c3AxX2RsX2xpc3RfcHV0KHN0cnVjdCB2c3AxX2RsX2xp c3QgKmRsKQo+ID4gIAkgKiBoYXMgYXQgbGVhc3Qgb25lIGJvZHksIHRodXMgd2UgcmVpbml0aWFs aXNlIHRoZSBlbnRyaWVzIGxpc3QuCj4gPiAgCSAqLwo+ID4gIAlkbC0+Ym9keTAtPm51bV9lbnRy aWVzID0gMDsKPiA+ICsJZGwtPmJvZHkwLT5udW1fcGF0Y2hlcyA9IDA7Cj4gPiAgCj4gPiAgCWxp c3RfYWRkX3RhaWwoJmRsLT5saXN0LCAmZGwtPmRsbS0+ZnJlZSk7Cj4gPiAgfQo+ID4gQEAgLTkz MCw2ICs5NjksMzYgQEAgdm9pZCB2c3AxX2RsX2xpc3RfY29tbWl0KHN0cnVjdCB2c3AxX2RsX2xp c3QgKmRsLCB1bnNpZ25lZCBpbnQgZGxfZmxhZ3MpCj4gPiAgICogRGlzcGxheSBMaXN0IE1hbmFn ZXIKPiA+ICAgKi8KPiA+ICAKPiA+ICsvKioKPiA+ICsgKiB2c3AxX2RsbV9pcnFfZGlzcGxheV9z dGFydCAtIERpc3BsYXkgbGlzdCBoYW5kbGVyIGZvciB0aGUgZGlzcGxheSBzdGFydAo+ID4gKyAq CWludGVycnVwdAo+ID4gKyAqIEBkbG06IHRoZSBkaXNwbGF5IGxpc3QgbWFuYWdlcgo+ID4gKyAq Cj4gPiArICogQXBwbHkgYWxsIHBhdGNoZXMgcmVnaXN0ZXJlZCBmb3IgdGhlIGFjdGl2ZSBkaXNw bGF5IGxpc3QuIFRoaXMgaXMgdXNlZCB0bwo+ID4gKyAqIGRpc2FibGUgd3JpdGViYWNrIGZvciB0 aGUgbmV4dCBmcmFtZS4KPiA+ICsgKi8KPiA+ICt2b2lkIHZzcDFfZGxtX2lycV9kaXNwbGF5X3N0 YXJ0KHN0cnVjdCB2c3AxX2RsX21hbmFnZXIgKmRsbSkKPiA+ICt7Cj4gPiArCXN0cnVjdCB2c3Ax X2RsX2JvZHkgKmRsYjsKPiA+ICsJc3RydWN0IHZzcDFfZGxfbGlzdCAqZGw7Cj4gPiArCXVuc2ln bmVkIGludCBpOwo+ID4gKwo+ID4gKwlzcGluX2xvY2soJmRsbS0+bG9jayk7Cj4gPiArCj4gPiAr CWRsID0gZGxtLT5hY3RpdmU7Cj4gPiArCWlmICghZGwpCj4gPiArCQlnb3RvIGRvbmU7Cj4gPiAr Cj4gPiArCWxpc3RfZm9yX2VhY2hfZW50cnkoZGxiLCAmZGwtPmJvZGllcywgbGlzdCkgewo+ID4g KwkJZm9yIChpID0gMDsgaSA8IGRsYi0+bnVtX3BhdGNoZXM7ICsraSkKPiA+ICsJCQlkbGItPnBh dGNoZXNbaV0uZW50cnktPmRhdGEgPSBkbGItPnBhdGNoZXNbaV0uZGF0YTsKPiA+ICsJCWRsYi0+ bnVtX3BhdGNoZXMgPSAwOwo+ID4gKwl9Cj4gPiArCj4gPiArZG9uZToKPiA+ICsJc3Bpbl91bmxv Y2soJmRsbS0+bG9jayk7Cj4gPiArfQo+ID4gKwo+ID4gIC8qKgo+ID4gICAqIHZzcDFfZGxtX2ly cV9mcmFtZV9lbmQgLSBEaXNwbGF5IGxpc3QgaGFuZGxlciBmb3IgdGhlIGZyYW1lIGVuZCBpbnRl cnJ1cHQKPiA+ICAgKiBAZGxtOiB0aGUgZGlzcGxheSBsaXN0IG1hbmFnZXIKPiA+IEBAIC05NDcs NiArMTAxNiw5IEBAIHZvaWQgdnNwMV9kbF9saXN0X2NvbW1pdChzdHJ1Y3QgdnNwMV9kbF9saXN0 ICpkbCwgdW5zaWduZWQgaW50IGRsX2ZsYWdzKQo+ID4gICAqCj4gPiAgICogVGhlIFZTUDFfRExf RlJBTUVfRU5EX0lOVEVSTkFMIGZsYWcgaW5kaWNhdGVzIHRoYXQgdGhlIGRpc3BsYXkgbGlzdCB0 aGF0IGp1c3QKPiA+ICAgKiBiZWNhbWUgYWN0aXZlIGhhZCBiZWVuIHF1ZXVlZCB3aXRoIHRoZSBp bnRlcm5hbCBub3RpZmljYXRpb24gZmxhZy4KPiA+ICsgKgo+ID4gKyAqIFRoZSBWU1AxX0RMX0ZS QU1FX0VORF9XUklURUJBQ0sgZmxhZyBpbmRpY2F0ZXMgdGhhdCB0aGUgcHJldmlvdXNseSBhY3Rp dmUKPiA+ICsgKiBkaXNwbGF5IGxpc3QgaGFkIGJlZW4gcXVldWVkIHdpdGggdGhlIHdyaXRlYmFj ayBmbGFnLgo+ID4gICAqLwo+ID4gIHVuc2lnbmVkIGludCB2c3AxX2RsbV9pcnFfZnJhbWVfZW5k KHN0cnVjdCB2c3AxX2RsX21hbmFnZXIgKmRsbSkKPiA+ICB7Cj4gPiBAQCAtOTg0LDYgKzEwNTYs MTcgQEAgdW5zaWduZWQgaW50IHZzcDFfZGxtX2lycV9mcmFtZV9lbmQoc3RydWN0IHZzcDFfZGxf bWFuYWdlciAqZGxtKQo+ID4gIAlpZiAoc3RhdHVzICYgVkk2X1NUQVRVU19GTERfU1REKGRsbS0+ aW5kZXgpKQo+ID4gIAkJZ290byBkb25lOwo+ID4gIAo+ID4gKwkvKgo+ID4gKwkgKiBJZiB0aGUg YWN0aXZlIGRpc3BsYXkgbGlzdCBoYXMgdGhlIHdyaXRlYmFjayBmbGFnIHNldCwgdGhlIGZyYW1l Cj4gPiArCSAqIGNvbXBsZXRpb24gbWFya3MgdGhlIGVuZCBvZiB0aGUgd3JpdGViYWNrIGNhcHR1 cmUuIFJldHVybiB0aGUKPiA+ICsJICogVlNQMV9ETF9GUkFNRV9FTkRfV1JJVEVCQUNLIGZsYWcg YW5kIHJlc2V0IHRoZSBkaXNwbGF5IGxpc3Qncwo+ID4gKwkgKiB3cml0ZWJhY2sgZmxhZy4KPiA+ ICsJICovCj4gPiArCWlmIChkbG0tPmFjdGl2ZSAmJiAoZGxtLT5hY3RpdmUtPmZsYWdzICYgVlNQ MV9ETF9GUkFNRV9FTkRfV1JJVEVCQUNLKSkgewo+ID4gKwkJZmxhZ3MgfD0gVlNQMV9ETF9GUkFN RV9FTkRfV1JJVEVCQUNLOwo+ID4gKwkJZGxtLT5hY3RpdmUtPmZsYWdzICY9IH5WU1AxX0RMX0ZS QU1FX0VORF9XUklURUJBQ0s7Cj4gPiArCX0KPiA+ICsKPiA+ICAJLyoKPiA+ICAJICogVGhlIGRl dmljZSBzdGFydHMgcHJvY2Vzc2luZyB0aGUgcXVldWVkIGRpc3BsYXkgbGlzdCByaWdodCBhZnRl ciB0aGUKPiA+ICAJICogZnJhbWUgZW5kIGludGVycnVwdC4gVGhlIGRpc3BsYXkgbGlzdCB0aHVz IGJlY29tZXMgYWN0aXZlLgo+ID4gZGlmZiAtLWdpdCBhL2RyaXZlcnMvbWVkaWEvcGxhdGZvcm0v dnNwMS92c3AxX2RsLmggYi9kcml2ZXJzL21lZGlhL3BsYXRmb3JtL3ZzcDEvdnNwMV9kbC5oCj4g PiBpbmRleCBlMGZkYjE0NWU2ZWQuLmNiYWEwYmYwY2JjMiAxMDA2NDQKPiA+IC0tLSBhL2RyaXZl cnMvbWVkaWEvcGxhdGZvcm0vdnNwMS92c3AxX2RsLmgKPiA+ICsrKyBiL2RyaXZlcnMvbWVkaWEv cGxhdGZvcm0vdnNwMS92c3AxX2RsLmgKPiA+IEBAIC0xOSw2ICsxOSw3IEBAIHN0cnVjdCB2c3Ax X2RsX21hbmFnZXI7Cj4gPiAgCj4gPiAgI2RlZmluZSBWU1AxX0RMX0ZSQU1FX0VORF9DT01QTEVU RUQJCUJJVCgwKQo+ID4gICNkZWZpbmUgVlNQMV9ETF9GUkFNRV9FTkRfSU5URVJOQUwJCUJJVCgx KQo+ID4gKyNkZWZpbmUgVlNQMV9ETF9GUkFNRV9FTkRfV1JJVEVCQUNLCQlCSVQoMikKPiA+ICAK PiA+ICAvKioKPiA+ICAgKiBzdHJ1Y3QgdnNwMV9kbF9leHRfY21kIC0gRXh0ZW5kZWQgRGlzcGxh eSBjb21tYW5kCj4gPiBAQCAtNTQsNiArNTUsNyBAQCBzdHJ1Y3QgdnNwMV9kbF9tYW5hZ2VyICp2 c3AxX2RsbV9jcmVhdGUoc3RydWN0IHZzcDFfZGV2aWNlICp2c3AxLAo+ID4gIAkJCQkJdW5zaWdu ZWQgaW50IHByZWFsbG9jKTsKPiA+ICB2b2lkIHZzcDFfZGxtX2Rlc3Ryb3koc3RydWN0IHZzcDFf ZGxfbWFuYWdlciAqZGxtKTsKPiA+ICB2b2lkIHZzcDFfZGxtX3Jlc2V0KHN0cnVjdCB2c3AxX2Rs X21hbmFnZXIgKmRsbSk7Cj4gPiArdm9pZCB2c3AxX2RsbV9pcnFfZGlzcGxheV9zdGFydChzdHJ1 Y3QgdnNwMV9kbF9tYW5hZ2VyICpkbG0pOwo+ID4gIHVuc2lnbmVkIGludCB2c3AxX2RsbV9pcnFf ZnJhbWVfZW5kKHN0cnVjdCB2c3AxX2RsX21hbmFnZXIgKmRsbSk7Cj4gPiAgc3RydWN0IHZzcDFf ZGxfYm9keSAqdnNwMV9kbG1fZGxfYm9keV9nZXQoc3RydWN0IHZzcDFfZGxfbWFuYWdlciAqZGxt KTsKPiA+ICAKPiA+IEBAIC03MSw2ICs3Myw4IEBAIHN0cnVjdCB2c3AxX2RsX2JvZHkgKnZzcDFf ZGxfYm9keV9nZXQoc3RydWN0IHZzcDFfZGxfYm9keV9wb29sICpwb29sKTsKPiA+ICB2b2lkIHZz cDFfZGxfYm9keV9wdXQoc3RydWN0IHZzcDFfZGxfYm9keSAqZGxiKTsKPiA+ICAKPiA+ICB2b2lk IHZzcDFfZGxfYm9keV93cml0ZShzdHJ1Y3QgdnNwMV9kbF9ib2R5ICpkbGIsIHUzMiByZWcsIHUz MiBkYXRhKTsKPiA+ICt2b2lkIHZzcDFfZGxfYm9keV93cml0ZV9wYXRjaChzdHJ1Y3QgdnNwMV9k bF9ib2R5ICpkbGIsIHUzMiByZWcsIHUzMiBkYXRhLAo+ID4gKwkJCSAgICAgIHUzMiBwYXRjaCk7 Cj4gPiAgaW50IHZzcDFfZGxfbGlzdF9hZGRfYm9keShzdHJ1Y3QgdnNwMV9kbF9saXN0ICpkbCwg c3RydWN0IHZzcDFfZGxfYm9keSAqZGxiKTsKPiA+ICBpbnQgdnNwMV9kbF9saXN0X2FkZF9jaGFp bihzdHJ1Y3QgdnNwMV9kbF9saXN0ICpoZWFkLCBzdHJ1Y3QgdnNwMV9kbF9saXN0ICpkbCk7Cj4g PiAgCj4gPiBkaWZmIC0tZ2l0IGEvZHJpdmVycy9tZWRpYS9wbGF0Zm9ybS92c3AxL3ZzcDFfZHJt LmMgYi9kcml2ZXJzL21lZGlhL3BsYXRmb3JtL3ZzcDEvdnNwMV9kcm0uYwo+ID4gaW5kZXggOWQy MGVmNWNkNWY4Li5lOWQwY2U0MzJhMmMgMTAwNjQ0Cj4gPiAtLS0gYS9kcml2ZXJzL21lZGlhL3Bs YXRmb3JtL3ZzcDEvdnNwMV9kcm0uYwo+ID4gKysrIGIvZHJpdmVycy9tZWRpYS9wbGF0Zm9ybS92 c3AxL3ZzcDFfZHJtLmMKPiA+IEBAIC0yMyw2ICsyMyw3IEBACj4gPiAgI2luY2x1ZGUgInZzcDFf cGlwZS5oIgo+ID4gICNpbmNsdWRlICJ2c3AxX3J3cGYuaCIKPiA+ICAjaW5jbHVkZSAidnNwMV91 aWYuaCIKPiA+ICsjaW5jbHVkZSAidnNwMV92aWRlby5oIgo+ID4gIAo+ID4gICNkZWZpbmUgQlJY X05BTUUoZSkJKGUpLT50eXBlID09IFZTUDFfRU5USVRZX0JSVSA/ICJCUlUiIDogIkJSUyIKPiA+ ICAKPiA+IEBAIC0zNCw3ICszNSw3IEBAIHN0YXRpYyB2b2lkIHZzcDFfZHVfcGlwZWxpbmVfZnJh bWVfZW5kKHN0cnVjdCB2c3AxX3BpcGVsaW5lICpwaXBlLAo+ID4gIAkJCQkgICAgICAgdW5zaWdu ZWQgaW50IGNvbXBsZXRpb24pCj4gPiAgewo+ID4gIAlzdHJ1Y3QgdnNwMV9kcm1fcGlwZWxpbmUg KmRybV9waXBlID0gdG9fdnNwMV9kcm1fcGlwZWxpbmUocGlwZSk7Cj4gPiAtCWJvb2wgY29tcGxl dGUgPSBjb21wbGV0aW9uID09IFZTUDFfRExfRlJBTUVfRU5EX0NPTVBMRVRFRDsKPiA+ICsJYm9v bCBjb21wbGV0ZSA9IGNvbXBsZXRpb24gJiBWU1AxX0RMX0ZSQU1FX0VORF9DT01QTEVURUQ7Cj4g PiAgCj4gPiAgCWlmIChkcm1fcGlwZS0+ZHVfY29tcGxldGUpIHsKPiA+ICAJCXN0cnVjdCB2c3Ax X2VudGl0eSAqdWlmID0gZHJtX3BpcGUtPnVpZjsKPiA+IEBAIC00OCw2ICs0OSw5IEBAIHN0YXRp YyB2b2lkIHZzcDFfZHVfcGlwZWxpbmVfZnJhbWVfZW5kKHN0cnVjdCB2c3AxX3BpcGVsaW5lICpw aXBlLAo+ID4gIAkJZHJtX3BpcGUtPmZvcmNlX2JyeF9yZWxlYXNlID0gZmFsc2U7Cj4gPiAgCQl3 YWtlX3VwKCZkcm1fcGlwZS0+d2FpdF9xdWV1ZSk7Cj4gPiAgCX0KPiA+ICsKPiA+ICsJaWYgKGNv bXBsZXRpb24gJiBWU1AxX0RMX0ZSQU1FX0VORF9XUklURUJBQ0spCj4gPiArCQl2c3AxX3ZpZGVv X3diX2ZyYW1lX2VuZChwaXBlLT5vdXRwdXQtPnZpZGVvKTsKPiA+ICB9Cj4gPiAgCj4gPiAgLyog LS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0t LS0tLS0tLS0tLS0tLS0tLS0tLS0KPiA+IEBAIC01NDEsNiArNTQ1LDggQEAgc3RhdGljIHZvaWQg dnNwMV9kdV9waXBlbGluZV9jb25maWd1cmUoc3RydWN0IHZzcDFfcGlwZWxpbmUgKnBpcGUpCj4g PiAgCj4gPiAgCWlmIChkcm1fcGlwZS0+Zm9yY2VfYnJ4X3JlbGVhc2UpCj4gPiAgCQlkbF9mbGFn cyB8PSBWU1AxX0RMX0ZSQU1FX0VORF9JTlRFUk5BTDsKPiA+ICsJaWYgKHBpcGUtPm91dHB1dC0+ d3JpdGViYWNrKQo+ID4gKwkJZGxfZmxhZ3MgfD0gVlNQMV9ETF9GUkFNRV9FTkRfV1JJVEVCQUNL Owo+ID4gIAo+ID4gIAlkbCA9IHZzcDFfZGxfbGlzdF9nZXQocGlwZS0+b3V0cHV0LT5kbG0pOwo+ ID4gIAlkbGIgPSB2c3AxX2RsX2xpc3RfZ2V0X2JvZHkwKGRsKTsKPiA+IEBAIC04NTksOCArODY1 LDE0IEBAIHZvaWQgdnNwMV9kdV9hdG9taWNfZmx1c2goc3RydWN0IGRldmljZSAqZGV2LCB1bnNp Z25lZCBpbnQgcGlwZV9pbmRleCwKPiA+ICAJZHJtX3BpcGUtPmNyYyA9IGNmZy0+Y3JjOwo+ID4g IAo+ID4gIAltdXRleF9sb2NrKCZ2c3AxLT5kcm0tPmxvY2spOwo+ID4gKwo+ID4gKwkvKiBJZiB3 ZSBoYXZlIGEgd3JpdGViYWNrIG5vZGUgYXR0YWNoZWQsIHVwZGF0ZSB0aGUgdmlkZW8gYnVmZmVy cy4gKi8KPiA+ICsJaWYgKHBpcGUtPm91dHB1dC0+dmlkZW8pCj4gPiArCQl2c3AxX3ZpZGVvX3di X3ByZXBhcmUocGlwZS0+b3V0cHV0LT52aWRlbyk7Cj4gPiArCj4gPiAgCXZzcDFfZHVfcGlwZWxp bmVfc2V0dXBfaW5wdXRzKHZzcDEsIHBpcGUpOwo+ID4gIAl2c3AxX2R1X3BpcGVsaW5lX2NvbmZp Z3VyZShwaXBlKTsKPiA+ICsKPiA+ICAJbXV0ZXhfdW5sb2NrKCZ2c3AxLT5kcm0tPmxvY2spOwo+ ID4gIH0KPiA+ICBFWFBPUlRfU1lNQk9MX0dQTCh2c3AxX2R1X2F0b21pY19mbHVzaCk7Cj4gPiBk aWZmIC0tZ2l0IGEvZHJpdmVycy9tZWRpYS9wbGF0Zm9ybS92c3AxL3ZzcDFfZHJ2LmMgYi9kcml2 ZXJzL21lZGlhL3BsYXRmb3JtL3ZzcDEvdnNwMV9kcnYuYwo+ID4gaW5kZXggYzY1MGU0NWJiMGFk Li4yMzVmZWJkMThmZmEgMTAwNjQ0Cj4gPiAtLS0gYS9kcml2ZXJzL21lZGlhL3BsYXRmb3JtL3Zz cDEvdnNwMV9kcnYuYwo+ID4gKysrIGIvZHJpdmVycy9tZWRpYS9wbGF0Zm9ybS92c3AxL3ZzcDFf ZHJ2LmMKPiA+IEBAIC02Myw2ICs2MywyMSBAQCBzdGF0aWMgaXJxcmV0dXJuX3QgdnNwMV9pcnFf aGFuZGxlcihpbnQgaXJxLCB2b2lkICpkYXRhKQo+ID4gIAkJCXZzcDFfcGlwZWxpbmVfZnJhbWVf ZW5kKHdwZi0+ZW50aXR5LnBpcGUpOwo+ID4gIAkJCXJldCA9IElSUV9IQU5ETEVEOwo+ID4gIAkJ fQo+ID4gKwo+ID4gKwkJLyoKPiA+ICsJCSAqIFByb2Nlc3MgdGhlIGRpc3BsYXkgc3RhcnQgaW50 ZXJydXB0IGFmdGVyIHRoZSBmcmFtZSBlbmQKPiA+ICsJCSAqIGludGVycnVwdCB0byBtYWtlIHN1 cmUgdGhlIGRpc3BsYXkgbGlzdCBxdWV1ZSBpcyBjb3JyZWN0bHkKPiA+ICsJCSAqIHVwZGF0ZWQg d2hlbiBwcm9jZXNzaW5nIHRoZSBkaXNwbGF5IHN0YXJ0Lgo+ID4gKwkJICovCj4gPiArCQlpZiAo d3BmLT5oYXNfd3JpdGViYWNrKSB7Cj4gPiArCQkJc3RhdHVzID0gdnNwMV9yZWFkKHZzcDEsIFZJ Nl9ESVNQX0lSUV9TVEEoaSkpOwo+ID4gKwkJCXZzcDFfd3JpdGUodnNwMSwgVkk2X0RJU1BfSVJR X1NUQShpKSwgfnN0YXR1cyAmIG1hc2spOwo+ID4gKwo+ID4gKwkJCWlmIChzdGF0dXMgJiBWSTZf RElTUF9JUlFfU1RBX0RTVCkgewo+ID4gKwkJCQl2c3AxX3BpcGVsaW5lX2Rpc3BsYXlfc3RhcnQo d3BmLT5lbnRpdHkucGlwZSk7Cj4gPiArCQkJCXJldCA9IElSUV9IQU5ETEVEOwo+ID4gKwkJCX0K PiA+ICsJCX0KPiA+ICAJfQo+ID4gIAo+ID4gIAlyZXR1cm4gcmV0Owo+ID4gQEAgLTQzNSw3ICs0 NTAsNyBAQCBzdGF0aWMgaW50IHZzcDFfY3JlYXRlX2VudGl0aWVzKHN0cnVjdCB2c3AxX2Rldmlj ZSAqdnNwMSkKPiA+ICAJCXZzcDEtPndwZltpXSA9IHdwZjsKPiA+ICAJCWxpc3RfYWRkX3RhaWwo JndwZi0+ZW50aXR5Lmxpc3RfZGV2LCAmdnNwMS0+ZW50aXRpZXMpOwo+ID4gIAo+ID4gLQkJaWYg KHZzcDEtPmluZm8tPnVhcGkpIHsKPiA+ICsJCWlmICh2c3AxLT5pbmZvLT51YXBpIHx8IHdwZi0+ aGFzX3dyaXRlYmFjaykgewo+ID4gIAkJCXN0cnVjdCB2c3AxX3ZpZGVvICp2aWRlbyA9IHZzcDFf dmlkZW9fY3JlYXRlKHZzcDEsIHdwZik7Cj4gPiAgCj4gPiAgCQkJaWYgKElTX0VSUih2aWRlbykp IHsKPiA+IGRpZmYgLS1naXQgYS9kcml2ZXJzL21lZGlhL3BsYXRmb3JtL3ZzcDEvdnNwMV9waXBl LmMgYi9kcml2ZXJzL21lZGlhL3BsYXRmb3JtL3ZzcDEvdnNwMV9waXBlLmMKPiA+IGluZGV4IDU0 ZmY1MzlmZmVhMC4uMDE2ODAwYzQ1YmMxIDEwMDY0NAo+ID4gLS0tIGEvZHJpdmVycy9tZWRpYS9w bGF0Zm9ybS92c3AxL3ZzcDFfcGlwZS5jCj4gPiArKysgYi9kcml2ZXJzL21lZGlhL3BsYXRmb3Jt L3ZzcDEvdnNwMV9waXBlLmMKPiA+IEBAIC0zMDksNiArMzA5LDExIEBAIGJvb2wgdnNwMV9waXBl bGluZV9yZWFkeShzdHJ1Y3QgdnNwMV9waXBlbGluZSAqcGlwZSkKPiA+ICAJcmV0dXJuIHBpcGUt PmJ1ZmZlcnNfcmVhZHkgPT0gbWFzazsKPiA+ICB9Cj4gPiAgCj4gPiArdm9pZCB2c3AxX3BpcGVs aW5lX2Rpc3BsYXlfc3RhcnQoc3RydWN0IHZzcDFfcGlwZWxpbmUgKnBpcGUpCj4gPiArewo+ID4g Kwl2c3AxX2RsbV9pcnFfZGlzcGxheV9zdGFydChwaXBlLT5vdXRwdXQtPmRsbSk7Cj4gPiArfQo+ ID4gKwo+ID4gIHZvaWQgdnNwMV9waXBlbGluZV9mcmFtZV9lbmQoc3RydWN0IHZzcDFfcGlwZWxp bmUgKnBpcGUpCj4gPiAgewo+ID4gIAl1bnNpZ25lZCBpbnQgZmxhZ3M7Cj4gPiBkaWZmIC0tZ2l0 IGEvZHJpdmVycy9tZWRpYS9wbGF0Zm9ybS92c3AxL3ZzcDFfcGlwZS5oIGIvZHJpdmVycy9tZWRp YS9wbGF0Zm9ybS92c3AxL3ZzcDFfcGlwZS5oCj4gPiBpbmRleCBhZTY0NmM5ZWYzMzcuLjgyZDUx Yjg5MWYxZSAxMDA2NDQKPiA+IC0tLSBhL2RyaXZlcnMvbWVkaWEvcGxhdGZvcm0vdnNwMS92c3Ax X3BpcGUuaAo+ID4gKysrIGIvZHJpdmVycy9tZWRpYS9wbGF0Zm9ybS92c3AxL3ZzcDFfcGlwZS5o Cj4gPiBAQCAtNDcsNiArNDcsMTEgQEAgc3RydWN0IHZzcDFfZm9ybWF0X2luZm8gewo+ID4gIAli b29sIGFscGhhOwo+ID4gIH07Cj4gPiAgCj4gPiArc3RhdGljIGlubGluZSBib29sIHZzcDFfZm9y bWF0X2lzX3JnYihjb25zdCBzdHJ1Y3QgdnNwMV9mb3JtYXRfaW5mbyAqaW5mbykKPiA+ICt7Cj4g PiArCXJldHVybiBpbmZvLT5tYnVzID09IE1FRElBX0JVU19GTVRfQVJHQjg4ODhfMVgzMjsKPiA+ ICt9Cj4gPiArCj4gPiAgZW51bSB2c3AxX3BpcGVsaW5lX3N0YXRlIHsKPiA+ICAJVlNQMV9QSVBF TElORV9TVE9QUEVELAo+ID4gIAlWU1AxX1BJUEVMSU5FX1JVTk5JTkcsCj4gPiBAQCAtMTU4LDYg KzE2Myw3IEBAIGJvb2wgdnNwMV9waXBlbGluZV9zdG9wcGVkKHN0cnVjdCB2c3AxX3BpcGVsaW5l ICpwaXBlKTsKPiA+ICBpbnQgdnNwMV9waXBlbGluZV9zdG9wKHN0cnVjdCB2c3AxX3BpcGVsaW5l ICpwaXBlKTsKPiA+ICBib29sIHZzcDFfcGlwZWxpbmVfcmVhZHkoc3RydWN0IHZzcDFfcGlwZWxp bmUgKnBpcGUpOwo+ID4gIAo+ID4gK3ZvaWQgdnNwMV9waXBlbGluZV9kaXNwbGF5X3N0YXJ0KHN0 cnVjdCB2c3AxX3BpcGVsaW5lICpwaXBlKTsKPiA+ICB2b2lkIHZzcDFfcGlwZWxpbmVfZnJhbWVf ZW5kKHN0cnVjdCB2c3AxX3BpcGVsaW5lICpwaXBlKTsKPiA+ICAKPiA+ICB2b2lkIHZzcDFfcGlw ZWxpbmVfcHJvcGFnYXRlX2FscGhhKHN0cnVjdCB2c3AxX3BpcGVsaW5lICpwaXBlLAo+ID4gZGlm ZiAtLWdpdCBhL2RyaXZlcnMvbWVkaWEvcGxhdGZvcm0vdnNwMS92c3AxX3J3cGYuaCBiL2RyaXZl cnMvbWVkaWEvcGxhdGZvcm0vdnNwMS92c3AxX3J3cGYuaAo+ID4gaW5kZXggNzA3NDJlY2Y3NjZm Li45MTA5OTBiMjc2MTcgMTAwNjQ0Cj4gPiAtLS0gYS9kcml2ZXJzL21lZGlhL3BsYXRmb3JtL3Zz cDEvdnNwMV9yd3BmLmgKPiA+ICsrKyBiL2RyaXZlcnMvbWVkaWEvcGxhdGZvcm0vdnNwMS92c3Ax X3J3cGYuaAo+ID4gQEAgLTM1LDYgKzM1LDcgQEAgc3RydWN0IHZzcDFfcndwZiB7Cj4gPiAgCXN0 cnVjdCB2NGwyX2N0cmxfaGFuZGxlciBjdHJsczsKPiA+ICAKPiA+ICAJc3RydWN0IHZzcDFfdmlk ZW8gKnZpZGVvOwo+ID4gKwlib29sIGhhc193cml0ZWJhY2s7Cj4gPiAgCj4gPiAgCXVuc2lnbmVk IGludCBtYXhfd2lkdGg7Cj4gPiAgCXVuc2lnbmVkIGludCBtYXhfaGVpZ2h0Owo+ID4gQEAgLTYx LDYgKzYyLDcgQEAgc3RydWN0IHZzcDFfcndwZiB7Cj4gPiAgCX0gZmxpcDsKPiA+ICAKPiA+ICAJ c3RydWN0IHZzcDFfcndwZl9tZW1vcnkgbWVtOwo+ID4gKwlib29sIHdyaXRlYmFjazsKPiA+ICAK PiA+ICAJc3RydWN0IHZzcDFfZGxfbWFuYWdlciAqZGxtOwo+ID4gIH07Cj4gPiBkaWZmIC0tZ2l0 IGEvZHJpdmVycy9tZWRpYS9wbGF0Zm9ybS92c3AxL3ZzcDFfdmlkZW8uYyBiL2RyaXZlcnMvbWVk aWEvcGxhdGZvcm0vdnNwMS92c3AxX3ZpZGVvLmMKPiA+IGluZGV4IDhmZWFhOGQ4OWZlOC4uMGFj MzQzMDI5MmQwIDEwMDY0NAo+ID4gLS0tIGEvZHJpdmVycy9tZWRpYS9wbGF0Zm9ybS92c3AxL3Zz cDFfdmlkZW8uYwo+ID4gKysrIGIvZHJpdmVycy9tZWRpYS9wbGF0Zm9ybS92c3AxL3ZzcDFfdmlk ZW8uYwo+ID4gQEAgLTM0LDcgKzM0LDYgQEAKPiA+ICAjaW5jbHVkZSAidnNwMV91ZHMuaCIKPiA+ ICAjaW5jbHVkZSAidnNwMV92aWRlby5oIgo+ID4gIAo+ID4gLSNkZWZpbmUgVlNQMV9WSURFT19E RUZfRk9STUFUCQlWNEwyX1BJWF9GTVRfWVVZVgo+ID4gICNkZWZpbmUgVlNQMV9WSURFT19ERUZf V0lEVEgJCTEwMjQKPiA+ICAjZGVmaW5lIFZTUDFfVklERU9fREVGX0hFSUdIVAkJNzY4Cj4gPiAg Cj4gPiBAQCAtNDUsNiArNDQsMTQgQEAKPiA+ICAgKiBIZWxwZXIgZnVuY3Rpb25zCj4gPiAgICov Cj4gPiAgCj4gPiArc3RhdGljIGlubGluZSB1bnNpZ25lZCBpbnQgdnNwMV92aWRlb19kZWZhdWx0 X2Zvcm1hdChzdHJ1Y3QgdnNwMV92aWRlbyAqdmlkZW8pCj4gPiArewo+ID4gKwlpZiAodmlkZW8t PnJ3cGYtPmhhc193cml0ZWJhY2spCj4gPiArCQlyZXR1cm4gVjRMMl9QSVhfRk1UX1JHQjI0Owo+ ID4gKwllbHNlCj4gPiArCQlyZXR1cm4gVjRMMl9QSVhfRk1UX1lVWVY7Cj4gPiArfQo+ID4gKwo+ ID4gIHN0YXRpYyBzdHJ1Y3QgdjRsMl9zdWJkZXYgKgo+ID4gIHZzcDFfdmlkZW9fcmVtb3RlX3N1 YmRldihzdHJ1Y3QgbWVkaWFfcGFkICpsb2NhbCwgdTMyICpwYWQpCj4gPiAgewo+ID4gQEAgLTEx MywxMSArMTIwLDEzIEBAIHN0YXRpYyBpbnQgX192c3AxX3ZpZGVvX3RyeV9mb3JtYXQoc3RydWN0 IHZzcDFfdmlkZW8gKnZpZGVvLAo+ID4gIAo+ID4gIAkvKgo+ID4gIAkgKiBSZXRyaWV2ZSBmb3Jt YXQgaW5mb3JtYXRpb24gYW5kIHNlbGVjdCB0aGUgZGVmYXVsdCBmb3JtYXQgaWYgdGhlCj4gPiAt CSAqIHJlcXVlc3RlZCBmb3JtYXQgaXNuJ3Qgc3VwcG9ydGVkLgo+ID4gKwkgKiByZXF1ZXN0ZWQg Zm9ybWF0IGlzbid0IHN1cHBvcnRlZC4gV3JpdGViYWNrIHZpZGVvIG5vZGVzIG9ubHkgc3VwcG9y dAo+ID4gKwkgKiBSR0IgZm9ybWF0cy4KPiA+ICAJICovCj4gPiAgCWluZm8gPSB2c3AxX2dldF9m b3JtYXRfaW5mbyh2aWRlby0+dnNwMSwgcGl4LT5waXhlbGZvcm1hdCk7Cj4gPiAtCWlmIChpbmZv ID09IE5VTEwpCj4gPiAtCQlpbmZvID0gdnNwMV9nZXRfZm9ybWF0X2luZm8odmlkZW8tPnZzcDEs IFZTUDFfVklERU9fREVGX0ZPUk1BVCk7Cj4gPiArCWlmICghaW5mbyB8fCAodmlkZW8tPnJ3cGYt Pmhhc193cml0ZWJhY2sgJiYgIXZzcDFfZm9ybWF0X2lzX3JnYihpbmZvKSkpCj4gPiArCQlpbmZv ID0gdnNwMV9nZXRfZm9ybWF0X2luZm8odmlkZW8tPnZzcDEsCj4gPiArCQkJCQkgICAgdnNwMV92 aWRlb19kZWZhdWx0X2Zvcm1hdCh2aWRlbykpOwo+ID4gIAo+ID4gIAlwaXgtPnBpeGVsZm9ybWF0 ID0gaW5mby0+Zm91cmNjOwo+ID4gIAlwaXgtPmNvbG9yc3BhY2UgPSBWNEwyX0NPTE9SU1BBQ0Vf U1JHQjsKPiA+IEBAIC05NDYsNiArOTU1LDEyMiBAQCBzdGF0aWMgY29uc3Qgc3RydWN0IHZiMl9v cHMgdnNwMV92aWRlb19xdWV1ZV9xb3BzID0gewo+ID4gIAkuc3RvcF9zdHJlYW1pbmcgPSB2c3Ax X3ZpZGVvX3N0b3Bfc3RyZWFtaW5nLAo+ID4gIH07Cj4gPiAgCj4gPiArLyogLS0tLS0tLS0tLS0t LS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0t LS0tLS0tLS0KPiA+ICsgKiBXcml0ZWJhY2sgU3VwcG9ydAo+ID4gKyAqLwo+ID4gKwo+ID4gK3N0 YXRpYyB2b2lkIHZzcDFfdmlkZW9fd2JfYnVmZmVyX3F1ZXVlKHN0cnVjdCB2YjJfYnVmZmVyICp2 YikKPiA+ICt7Cj4gPiArCXN0cnVjdCB2YjJfdjRsMl9idWZmZXIgKnZidWYgPSB0b192YjJfdjRs Ml9idWZmZXIodmIpOwo+ID4gKwlzdHJ1Y3QgdnNwMV92aWRlbyAqdmlkZW8gPSB2YjJfZ2V0X2Ry dl9wcml2KHZiLT52YjJfcXVldWUpOwo+ID4gKwlzdHJ1Y3QgdnNwMV92YjJfYnVmZmVyICpidWYg PSB0b192c3AxX3ZiMl9idWZmZXIodmJ1Zik7Cj4gPiArCXVuc2lnbmVkIGxvbmcgZmxhZ3M7Cj4g PiArCj4gPiArCXNwaW5fbG9ja19pcnFzYXZlKCZ2aWRlby0+aXJxbG9jaywgZmxhZ3MpOwo+ID4g KwlsaXN0X2FkZF90YWlsKCZidWYtPnF1ZXVlLCAmdmlkZW8tPmlycXF1ZXVlKTsKPiA+ICsJc3Bp bl91bmxvY2tfaXJxcmVzdG9yZSgmdmlkZW8tPmlycWxvY2ssIGZsYWdzKTsKPiA+ICt9Cj4gPiAr Cj4gPiArc3RhdGljIGludCB2c3AxX3ZpZGVvX3diX3N0YXJ0X3N0cmVhbWluZyhzdHJ1Y3QgdmIy X3F1ZXVlICp2cSwKPiA+ICsJCQkJCSB1bnNpZ25lZCBpbnQgY291bnQpCj4gPiArewo+ID4gKwlz dHJ1Y3QgdnNwMV92aWRlbyAqdmlkZW8gPSB2YjJfZ2V0X2Rydl9wcml2KHZxKTsKPiA+ICsKPiA+ ICsJdmlkZW8tPndiX3J1bm5pbmcgPSB0cnVlOwo+ID4gKwlyZXR1cm4gMDsKPiA+ICt9Cj4gPiAr Cj4gPiArc3RhdGljIGJvb2wgdnNwMV92aWRlb193Yl9zdG9wcGVkKHN0cnVjdCB2c3AxX3ZpZGVv ICp2aWRlbykKPiA+ICt7Cj4gPiArCXVuc2lnbmVkIGxvbmcgZmxhZ3M7Cj4gPiArCWJvb2wgc3Rv cHBlZDsKPiA+ICsKPiA+ICsJc3Bpbl9sb2NrX2lycXNhdmUoJnZpZGVvLT5pcnFsb2NrLCBmbGFn cyk7Cj4gPiArCXN0b3BwZWQgPSBsaXN0X2VtcHR5KCZ2aWRlby0+d2JfcXVldWUpOwo+ID4gKwlz cGluX3VubG9ja19pcnFyZXN0b3JlKCZ2aWRlby0+aXJxbG9jaywgZmxhZ3MpOwo+ID4gKwo+ID4g KwlyZXR1cm4gc3RvcHBlZDsKPiA+ICt9Cj4gPiArCj4gPiArc3RhdGljIHZvaWQgdnNwMV92aWRl b193Yl9zdG9wX3N0cmVhbWluZyhzdHJ1Y3QgdmIyX3F1ZXVlICp2cSkKPiA+ICt7Cj4gPiArCXN0 cnVjdCB2c3AxX3ZpZGVvICp2aWRlbyA9IHZiMl9nZXRfZHJ2X3ByaXYodnEpOwo+ID4gKwlzdHJ1 Y3QgdnNwMV9yd3BmICpyd3BmID0gdmlkZW8tPnJ3cGY7Cj4gPiArCXN0cnVjdCB2c3AxX3BpcGVs aW5lICpwaXBlID0gcndwZi0+ZW50aXR5LnBpcGU7Cj4gPiArCXVuc2lnbmVkIGxvbmcgZmxhZ3M7 Cj4gPiArCWludCByZXQ7Cj4gPiArCj4gPiArCS8qIERpc2FibGUgd3JpdGViYWNrIGFuZCB3YWl0 IGZvciB0aGUgcGVuZGluZyBmcmFtZXMgdG8gY29tcGxldGUuICovCj4gPiArCXNwaW5fbG9ja19p cnFzYXZlKCZ2aWRlby0+aXJxbG9jaywgZmxhZ3MpOwo+ID4gKwl2aWRlby0+d2JfcnVubmluZyA9 IGZhbHNlOwo+ID4gKwlzcGluX3VubG9ja19pcnFyZXN0b3JlKCZ2aWRlby0+aXJxbG9jaywgZmxh Z3MpOwo+ID4gKwo+ID4gKwlyZXQgPSB3YWl0X2V2ZW50X3RpbWVvdXQocGlwZS0+d3EsIHZzcDFf dmlkZW9fd2Jfc3RvcHBlZCh2aWRlbyksCj4gPiArCQkJCSBtc2Vjc190b19qaWZmaWVzKDUwMCkp Owo+ID4gKwlpZiAocmV0ID09IDApIHsKPiA+ICsJCWRldl9lcnIodmlkZW8tPnZzcDEtPmRldiwg IndyaXRlYmFjayBzdG9wIHRpbWVvdXRcbiIpOwo+ID4gKwkJbGlzdF9zcGxpY2VfaW5pdCgmdmlk ZW8tPndiX3F1ZXVlLCAmdmlkZW8tPmlycXF1ZXVlKTsKPiA+ICsJfQo+ID4gKwo+ID4gKwl2c3Ax X3ZpZGVvX3JlbGVhc2VfYnVmZmVycyh2aWRlbyk7Cj4gPiArfQo+ID4gKwo+ID4gK3N0YXRpYyBj b25zdCBzdHJ1Y3QgdmIyX29wcyB2c3AxX3ZpZGVvX3diX3F1ZXVlX3FvcHMgPSB7Cj4gPiArCS5x dWV1ZV9zZXR1cCA9IHZzcDFfdmlkZW9fcXVldWVfc2V0dXAsCj4gPiArCS5idWZfcHJlcGFyZSA9 IHZzcDFfdmlkZW9fYnVmZmVyX3ByZXBhcmUsCj4gPiArCS5idWZfcXVldWUgPSB2c3AxX3ZpZGVv X3diX2J1ZmZlcl9xdWV1ZSwKPiA+ICsJLndhaXRfcHJlcGFyZSA9IHZiMl9vcHNfd2FpdF9wcmVw YXJlLAo+ID4gKwkud2FpdF9maW5pc2ggPSB2YjJfb3BzX3dhaXRfZmluaXNoLAo+ID4gKwkuc3Rh cnRfc3RyZWFtaW5nID0gdnNwMV92aWRlb193Yl9zdGFydF9zdHJlYW1pbmcsCj4gPiArCS5zdG9w X3N0cmVhbWluZyA9IHZzcDFfdmlkZW9fd2Jfc3RvcF9zdHJlYW1pbmcsCj4gPiArfTsKPiA+ICsK PiA+ICt2b2lkIHZzcDFfdmlkZW9fd2JfcHJlcGFyZShzdHJ1Y3QgdnNwMV92aWRlbyAqdmlkZW8p Cj4gPiArewo+ID4gKwlzdHJ1Y3QgdnNwMV92YjJfYnVmZmVyICpidWY7Cj4gPiArCXVuc2lnbmVk IGxvbmcgZmxhZ3M7Cj4gPiArCj4gPiArCS8qCj4gPiArCSAqIElmIHdyaXRlYmFjayBpcyBkaXNh YmxlZCwgcmV0dXJuIGltbWVkaWF0ZWx5LiBPdGhlcndpc2UgcmVtb3ZlIHRoZQo+ID4gKwkgKiBm aXJzdCBidWZmZXIgZnJvbSB0aGUgaXJxcXVldWUsIGFkZCBpdCB0byB0aGUgd3JpdGViYWNrIHF1 ZXVlIGFuZAo+ID4gKwkgKiBjb25maWd1cmUgdGhlIFdQRiBmb3Igd3JpdGViYWNrLgo+ID4gKwkg Ki8KPiA+ICsKPiA+ICsJc3Bpbl9sb2NrX2lycXNhdmUoJnZpZGVvLT5pcnFsb2NrLCBmbGFncyk7 Cj4gPiArCj4gPiArCWlmICghdmlkZW8tPndiX3J1bm5pbmcpIHsKPiA+ICsJCXNwaW5fdW5sb2Nr X2lycXJlc3RvcmUoJnZpZGVvLT5pcnFsb2NrLCBmbGFncyk7Cj4gPiArCQlyZXR1cm47Cj4gPiAr CX0KPiA+ICsKPiA+ICsJYnVmID0gbGlzdF9maXJzdF9lbnRyeV9vcl9udWxsKCZ2aWRlby0+aXJx cXVldWUsIHN0cnVjdCB2c3AxX3ZiMl9idWZmZXIsCj4gPiArCQkJCSAgICAgICBxdWV1ZSk7Cj4g PiArCWlmIChidWYpCj4gPiArCQlsaXN0X21vdmVfdGFpbCgmYnVmLT5xdWV1ZSwgJnZpZGVvLT53 Yl9xdWV1ZSk7Cj4gPiArCj4gPiArCXNwaW5fdW5sb2NrX2lycXJlc3RvcmUoJnZpZGVvLT5pcnFs b2NrLCBmbGFncyk7Cj4gPiArCj4gPiArCWlmIChidWYpIHsKPiA+ICsJCXZpZGVvLT5yd3BmLT5t ZW0gPSBidWYtPm1lbTsKPiA+ICsJCXZpZGVvLT5yd3BmLT53cml0ZWJhY2sgPSB0cnVlOwo+ID4g Kwl9Cj4gPiArfQo+ID4gKwo+ID4gK3ZvaWQgdnNwMV92aWRlb193Yl9mcmFtZV9lbmQoc3RydWN0 IHZzcDFfdmlkZW8gKnZpZGVvKQo+ID4gK3sKPiA+ICsJc3RydWN0IHZzcDFfdmIyX2J1ZmZlciAq ZG9uZTsKPiA+ICsJdW5zaWduZWQgbG9uZyBmbGFnczsKPiA+ICsKPiA+ICsJLyogQ29tcGxldGUg dGhlIGZpcnN0IGJ1ZmZlciBmcm9tIHRoZSB3cml0ZWJhY2sgcXVldWUuICovCj4gPiArCXNwaW5f bG9ja19pcnFzYXZlKCZ2aWRlby0+aXJxbG9jaywgZmxhZ3MpOwo+ID4gKwlkb25lID0gbGlzdF9m aXJzdF9lbnRyeSgmdmlkZW8tPndiX3F1ZXVlLCBzdHJ1Y3QgdnNwMV92YjJfYnVmZmVyLAo+ID4g KwkJCQlxdWV1ZSk7Cj4gPiArCWxpc3RfZGVsKCZkb25lLT5xdWV1ZSk7Cj4gPiArCXNwaW5fdW5s b2NrX2lycXJlc3RvcmUoJnZpZGVvLT5pcnFsb2NrLCBmbGFncyk7Cj4gPiArCj4gPiArCXZzcDFf dmlkZW9fY29tcGxldGVfYnVmZmVyKHZpZGVvLCBkb25lKTsKPiA+ICt9Cj4gPiArCj4gPiAgLyog LS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0t LS0tLS0tLS0tLS0tLS0tLS0tLS0KPiA+ICAgKiBWNEwyIGlvY3Rscwo+ID4gICAqLwo+ID4gQEAg LTEwNDUsNiArMTE3MCwxMyBAQCB2c3AxX3ZpZGVvX3N0cmVhbW9uKHN0cnVjdCBmaWxlICpmaWxl LCB2b2lkICpmaCwgZW51bSB2NGwyX2J1Zl90eXBlIHR5cGUpCj4gPiAgCWlmICh2aWRlby0+cXVl dWUub3duZXIgJiYgdmlkZW8tPnF1ZXVlLm93bmVyICE9IGZpbGUtPnByaXZhdGVfZGF0YSkKPiA+ ICAJCXJldHVybiAtRUJVU1k7Cj4gPiAgCj4gPiArCS8qCj4gPiArCSAqIFdyaXRlYmFjayB2aWRl byBkZXZpY2VzIGRvbid0IG5lZWQgdG8gaW50ZXJmYWNlIHdpdGggdGhlIHBpcGVsaW5lIG9yCj4g PiArCSAqIHZlcmlmeSBmb3JtYXRzLCBqdXN0IHR1cm4gc3RyZWFtaW5nIG9uLgo+ID4gKwkgKi8K PiA+ICsJaWYgKHZpZGVvLT5yd3BmLT5oYXNfd3JpdGViYWNrKQo+ID4gKwkJcmV0dXJuIHZiMl9z dHJlYW1vbigmdmlkZW8tPnF1ZXVlLCB0eXBlKTsKPiA+ICsKPiA+ICAJLyoKPiA+ICAJICogR2V0 IGEgcGlwZWxpbmUgZm9yIHRoZSB2aWRlbyBub2RlIGFuZCBzdGFydCBzdHJlYW1pbmcgb24gaXQu IE5vIGxpbmsKPiA+ICAJICogdG91Y2hpbmcgYW4gZW50aXR5IGluIHRoZSBwaXBlbGluZSBjYW4g YmUgYWN0aXZhdGVkIG9yIGRlYWN0aXZhdGVkCj4gPiBAQCAtMTI3Myw3ICsxNDA1LDcgQEAgc3Ry dWN0IHZzcDFfdmlkZW8gKnZzcDFfdmlkZW9fY3JlYXRlKHN0cnVjdCB2c3AxX2RldmljZSAqdnNw MSwKPiA+ICAJCXZpZGVvLT5wYWQuZmxhZ3MgPSBNRURJQV9QQURfRkxfU09VUkNFOwo+ID4gIAkJ dmlkZW8tPnZpZGVvLnZmbF9kaXIgPSBWRkxfRElSX1RYOwo+ID4gIAl9IGVsc2Ugewo+ID4gLQkJ ZGlyZWN0aW9uID0gIm91dHB1dCI7Cj4gPiArCQlkaXJlY3Rpb24gPSByd3BmLT5oYXNfd3JpdGVi YWNrID8gIndyaXRlYmFjayIgOiAib3V0cHV0IjsKPiA+ICAJCXZpZGVvLT50eXBlID0gVjRMMl9C VUZfVFlQRV9WSURFT19DQVBUVVJFX01QTEFORTsKPiA+ICAJCXZpZGVvLT5wYWQuZmxhZ3MgPSBN RURJQV9QQURfRkxfU0lOSzsKPiA+ICAJCXZpZGVvLT52aWRlby52ZmxfZGlyID0gVkZMX0RJUl9S WDsKPiA+IEBAIC0xMjgyLDYgKzE0MTQsNyBAQCBzdHJ1Y3QgdnNwMV92aWRlbyAqdnNwMV92aWRl b19jcmVhdGUoc3RydWN0IHZzcDFfZGV2aWNlICp2c3AxLAo+ID4gIAltdXRleF9pbml0KCZ2aWRl by0+bG9jayk7Cj4gPiAgCXNwaW5fbG9ja19pbml0KCZ2aWRlby0+aXJxbG9jayk7Cj4gPiAgCUlO SVRfTElTVF9IRUFEKCZ2aWRlby0+aXJxcXVldWUpOwo+ID4gKwlJTklUX0xJU1RfSEVBRCgmdmlk ZW8tPndiX3F1ZXVlKTsKPiA+ICAKPiA+ICAJLyogSW5pdGlhbGl6ZSB0aGUgbWVkaWEgZW50aXR5 Li4uICovCj4gPiAgCXJldCA9IG1lZGlhX2VudGl0eV9wYWRzX2luaXQoJnZpZGVvLT52aWRlby5l bnRpdHksIDEsICZ2aWRlby0+cGFkKTsKPiA+IEBAIC0xMjg5LDcgKzE0MjIsNyBAQCBzdHJ1Y3Qg dnNwMV92aWRlbyAqdnNwMV92aWRlb19jcmVhdGUoc3RydWN0IHZzcDFfZGV2aWNlICp2c3AxLAo+ ID4gIAkJcmV0dXJuIEVSUl9QVFIocmV0KTsKPiA+ICAKPiA+ICAJLyogLi4uIGFuZCB0aGUgZm9y bWF0IC4uLiAqLwo+ID4gLQlyd3BmLT5mb3JtYXQucGl4ZWxmb3JtYXQgPSBWU1AxX1ZJREVPX0RF Rl9GT1JNQVQ7Cj4gPiArCXJ3cGYtPmZvcm1hdC5waXhlbGZvcm1hdCA9IHZzcDFfdmlkZW9fZGVm YXVsdF9mb3JtYXQodmlkZW8pOwo+ID4gIAlyd3BmLT5mb3JtYXQud2lkdGggPSBWU1AxX1ZJREVP X0RFRl9XSURUSDsKPiA+ICAJcndwZi0+Zm9ybWF0LmhlaWdodCA9IFZTUDFfVklERU9fREVGX0hF SUdIVDsKPiA+ICAJX192c3AxX3ZpZGVvX3RyeV9mb3JtYXQodmlkZW8sICZyd3BmLT5mb3JtYXQs ICZyd3BmLT5mbXRpbmZvKTsKPiA+IEBAIC0xMzEwLDcgKzE0NDMsMTAgQEAgc3RydWN0IHZzcDFf dmlkZW8gKnZzcDFfdmlkZW9fY3JlYXRlKHN0cnVjdCB2c3AxX2RldmljZSAqdnNwMSwKPiA+ICAJ dmlkZW8tPnF1ZXVlLmxvY2sgPSAmdmlkZW8tPmxvY2s7Cj4gPiAgCXZpZGVvLT5xdWV1ZS5kcnZf cHJpdiA9IHZpZGVvOwo+ID4gIAl2aWRlby0+cXVldWUuYnVmX3N0cnVjdF9zaXplID0gc2l6ZW9m KHN0cnVjdCB2c3AxX3ZiMl9idWZmZXIpOwo+ID4gLQl2aWRlby0+cXVldWUub3BzID0gJnZzcDFf dmlkZW9fcXVldWVfcW9wczsKPiA+ICsJaWYgKHJ3cGYtPmhhc193cml0ZWJhY2spCj4gPiArCQl2 aWRlby0+cXVldWUub3BzID0gJnZzcDFfdmlkZW9fd2JfcXVldWVfcW9wczsKPiA+ICsJZWxzZQo+ ID4gKwkJdmlkZW8tPnF1ZXVlLm9wcyA9ICZ2c3AxX3ZpZGVvX3F1ZXVlX3FvcHM7Cj4gPiAgCXZp ZGVvLT5xdWV1ZS5tZW1fb3BzID0gJnZiMl9kbWFfY29udGlnX21lbW9wczsKPiA+ICAJdmlkZW8t PnF1ZXVlLnRpbWVzdGFtcF9mbGFncyA9IFY0TDJfQlVGX0ZMQUdfVElNRVNUQU1QX0NPUFk7Cj4g PiAgCXZpZGVvLT5xdWV1ZS5kZXYgPSB2aWRlby0+dnNwMS0+YnVzX21hc3RlcjsKPiA+IGRpZmYg LS1naXQgYS9kcml2ZXJzL21lZGlhL3BsYXRmb3JtL3ZzcDEvdnNwMV92aWRlby5oIGIvZHJpdmVy cy9tZWRpYS9wbGF0Zm9ybS92c3AxL3ZzcDFfdmlkZW8uaAo+ID4gaW5kZXggZjNjZjVlMmZkZjVh Li4xM2IzNTdiMDdlZTIgMTAwNjQ0Cj4gPiAtLS0gYS9kcml2ZXJzL21lZGlhL3BsYXRmb3JtL3Zz cDEvdnNwMV92aWRlby5oCj4gPiArKysgYi9kcml2ZXJzL21lZGlhL3BsYXRmb3JtL3ZzcDEvdnNw MV92aWRlby5oCj4gPiBAQCAtNDQsNiArNDQsOSBAQCBzdHJ1Y3QgdnNwMV92aWRlbyB7Cj4gPiAg CXN0cnVjdCB2YjJfcXVldWUgcXVldWU7Cj4gPiAgCXNwaW5sb2NrX3QgaXJxbG9jazsKPiA+ICAJ c3RydWN0IGxpc3RfaGVhZCBpcnFxdWV1ZTsKPiA+ICsKPiA+ICsJYm9vbCB3Yl9ydW5uaW5nOwo+ ID4gKwlzdHJ1Y3QgbGlzdF9oZWFkIHdiX3F1ZXVlOwo+ID4gIH07Cj4gPiAgCj4gPiAgc3RhdGlj IGlubGluZSBzdHJ1Y3QgdnNwMV92aWRlbyAqdG9fdnNwMV92aWRlbyhzdHJ1Y3QgdmlkZW9fZGV2 aWNlICp2ZGV2KQo+ID4gQEAgLTU0LDYgKzU3LDkgQEAgc3RhdGljIGlubGluZSBzdHJ1Y3QgdnNw MV92aWRlbyAqdG9fdnNwMV92aWRlbyhzdHJ1Y3QgdmlkZW9fZGV2aWNlICp2ZGV2KQo+ID4gIHZv aWQgdnNwMV92aWRlb19zdXNwZW5kKHN0cnVjdCB2c3AxX2RldmljZSAqdnNwMSk7Cj4gPiAgdm9p ZCB2c3AxX3ZpZGVvX3Jlc3VtZShzdHJ1Y3QgdnNwMV9kZXZpY2UgKnZzcDEpOwo+ID4gIAo+ID4g K3ZvaWQgdnNwMV92aWRlb193Yl9wcmVwYXJlKHN0cnVjdCB2c3AxX3ZpZGVvICp2aWRlbyk7Cj4g PiArdm9pZCB2c3AxX3ZpZGVvX3diX2ZyYW1lX2VuZChzdHJ1Y3QgdnNwMV92aWRlbyAqdmlkZW8p Owo+ID4gKwo+ID4gIHN0cnVjdCB2c3AxX3ZpZGVvICp2c3AxX3ZpZGVvX2NyZWF0ZShzdHJ1Y3Qg dnNwMV9kZXZpY2UgKnZzcDEsCj4gPiAgCQkJCSAgICAgc3RydWN0IHZzcDFfcndwZiAqcndwZik7 Cj4gPiAgdm9pZCB2c3AxX3ZpZGVvX2NsZWFudXAoc3RydWN0IHZzcDFfdmlkZW8gKnZpZGVvKTsK PiA+IGRpZmYgLS1naXQgYS9kcml2ZXJzL21lZGlhL3BsYXRmb3JtL3ZzcDEvdnNwMV93cGYuYyBi L2RyaXZlcnMvbWVkaWEvcGxhdGZvcm0vdnNwMS92c3AxX3dwZi5jCj4gPiBpbmRleCAxOGM0OWUz YTc4NzUuLjgxNjUwYTYyNTE4NSAxMDA2NDQKPiA+IC0tLSBhL2RyaXZlcnMvbWVkaWEvcGxhdGZv cm0vdnNwMS92c3AxX3dwZi5jCj4gPiArKysgYi9kcml2ZXJzL21lZGlhL3BsYXRmb3JtL3ZzcDEv dnNwMV93cGYuYwo+ID4gQEAgLTI0MCw2ICsyNDAsNyBAQCBzdGF0aWMgdm9pZCB3cGZfY29uZmln dXJlX3N0cmVhbShzdHJ1Y3QgdnNwMV9lbnRpdHkgKmVudGl0eSwKPiA+ICAJc3RydWN0IHZzcDFf ZGV2aWNlICp2c3AxID0gd3BmLT5lbnRpdHkudnNwMTsKPiA+ICAJY29uc3Qgc3RydWN0IHY0bDJf bWJ1c19mcmFtZWZtdCAqc291cmNlX2Zvcm1hdDsKPiA+ICAJY29uc3Qgc3RydWN0IHY0bDJfbWJ1 c19mcmFtZWZtdCAqc2lua19mb3JtYXQ7Cj4gPiArCXVuc2lnbmVkIGludCBpbmRleCA9IHdwZi0+ ZW50aXR5LmluZGV4Owo+ID4gIAl1bnNpZ25lZCBpbnQgaTsKPiA+ICAJdTMyIG91dGZtdCA9IDA7 Cj4gPiAgCXUzMiBzcmNycGYgPSAwOwo+ID4gQEAgLTI1MCw4ICsyNTEsOSBAQCBzdGF0aWMgdm9p ZCB3cGZfY29uZmlndXJlX3N0cmVhbShzdHJ1Y3QgdnNwMV9lbnRpdHkgKmVudGl0eSwKPiA+ICAJ c291cmNlX2Zvcm1hdCA9IHZzcDFfZW50aXR5X2dldF9wYWRfZm9ybWF0KCZ3cGYtPmVudGl0eSwK PiA+ICAJCQkJCQkgICB3cGYtPmVudGl0eS5jb25maWcsCj4gPiAgCQkJCQkJICAgUldQRl9QQURf U09VUkNFKTsKPiA+ICsKPiA+ICAJLyogRm9ybWF0ICovCj4gPiAtCWlmICghcGlwZS0+bGlmKSB7 Cj4gPiArCWlmICghcGlwZS0+bGlmIHx8IHdwZi0+d3JpdGViYWNrKSB7Cj4gPiAgCQljb25zdCBz dHJ1Y3QgdjRsMl9waXhfZm9ybWF0X21wbGFuZSAqZm9ybWF0ID0gJndwZi0+Zm9ybWF0Owo+ID4g IAkJY29uc3Qgc3RydWN0IHZzcDFfZm9ybWF0X2luZm8gKmZtdGluZm8gPSB3cGYtPmZtdGluZm87 Cj4gPiAgCj4gPiBAQCAtMjc2LDggKzI3OCw3IEBAIHN0YXRpYyB2b2lkIHdwZl9jb25maWd1cmVf c3RyZWFtKHN0cnVjdCB2c3AxX2VudGl0eSAqZW50aXR5LAo+ID4gIAo+ID4gIAkJdnNwMV93cGZf d3JpdGUod3BmLCBkbGIsIFZJNl9XUEZfRFNXQVAsIGZtdGluZm8tPnN3YXApOwo+ID4gIAo+ID4g LQkJaWYgKHZzcDFfZmVhdHVyZSh2c3AxLCBWU1AxX0hBU19XUEZfSEZMSVApICYmCj4gPiAtCQkg ICAgd3BmLT5lbnRpdHkuaW5kZXggPT0gMCkKPiA+ICsJCWlmICh2c3AxX2ZlYXR1cmUodnNwMSwg VlNQMV9IQVNfV1BGX0hGTElQKSAmJiBpbmRleCA9PSAwKQo+ID4gIAkJCXZzcDFfd3BmX3dyaXRl KHdwZiwgZGxiLCBWSTZfV1BGX1JPVF9DVFJMLAo+ID4gIAkJCQkgICAgICAgVkk2X1dQRl9ST1Rf Q1RSTF9MTjE2IHwKPiA+ICAJCQkJICAgICAgICgyNTYgPDwgVkk2X1dQRl9ST1RfQ1RSTF9MTUVN X1dEX1NISUZUKSk7Cj4gPiBAQCAtMjg4LDExICsyODksOSBAQCBzdGF0aWMgdm9pZCB3cGZfY29u ZmlndXJlX3N0cmVhbShzdHJ1Y3QgdnNwMV9lbnRpdHkgKmVudGl0eSwKPiA+ICAKPiA+ICAJd3Bm LT5vdXRmbXQgPSBvdXRmbXQ7Cj4gPiAgCj4gPiAtCXZzcDFfZGxfYm9keV93cml0ZShkbGIsIFZJ Nl9EUFJfV1BGX0ZQT1JDSCh3cGYtPmVudGl0eS5pbmRleCksCj4gPiArCXZzcDFfZGxfYm9keV93 cml0ZShkbGIsIFZJNl9EUFJfV1BGX0ZQT1JDSChpbmRleCksCj4gPiAgCQkJICAgVkk2X0RQUl9X UEZfRlBPUkNIX0ZQX1dQRk4pOwo+ID4gIAo+ID4gLQl2c3AxX2RsX2JvZHlfd3JpdGUoZGxiLCBW STZfV1BGX1dSQkNLX0NUUkwod3BmLT5lbnRpdHkuaW5kZXgpLCAwKTsKPiA+IC0KPiA+ICAJLyoK PiA+ICAJICogU291cmNlcy4gSWYgdGhlIHBpcGVsaW5lIGhhcyBhIHNpbmdsZSBpbnB1dCBhbmQg QlJ4IGlzIG5vdCB1c2VkLAo+ID4gIAkgKiBjb25maWd1cmUgaXQgYXMgdGhlIG1hc3RlciBsYXll ci4gT3RoZXJ3aXNlIGNvbmZpZ3VyZSBhbGwKPiA+IEBAIC0zMTgsOSArMzE3LDI0IEBAIHN0YXRp YyB2b2lkIHdwZl9jb25maWd1cmVfc3RyZWFtKHN0cnVjdCB2c3AxX2VudGl0eSAqZW50aXR5LAo+ ID4gIAl2c3AxX3dwZl93cml0ZSh3cGYsIGRsYiwgVkk2X1dQRl9TUkNSUEYsIHNyY3JwZik7Cj4g PiAgCj4gPiAgCS8qIEVuYWJsZSBpbnRlcnJ1cHRzLiAqLwo+ID4gLQl2c3AxX2RsX2JvZHlfd3Jp dGUoZGxiLCBWSTZfV1BGX0lSUV9TVEEod3BmLT5lbnRpdHkuaW5kZXgpLCAwKTsKPiA+IC0JdnNw MV9kbF9ib2R5X3dyaXRlKGRsYiwgVkk2X1dQRl9JUlFfRU5CKHdwZi0+ZW50aXR5LmluZGV4KSwK PiA+ICsJdnNwMV9kbF9ib2R5X3dyaXRlKGRsYiwgVkk2X1dQRl9JUlFfU1RBKGluZGV4KSwgMCk7 Cj4gPiArCXZzcDFfZGxfYm9keV93cml0ZShkbGIsIFZJNl9XUEZfSVJRX0VOQihpbmRleCksCj4g PiAgCQkJICAgVkk2X1dGUF9JUlFfRU5CX0RGRUUpOwo+ID4gKwo+ID4gKwkvKgo+ID4gKwkgKiBD b25maWd1cmUgd3JpdGViYWNrIGZvciBkaXNwbGF5IHBpcGVsaW5lcy4gVGhlIHdwZiB3cml0ZWJh Y2sgZmxhZyBpcwo+ID4gKwkgKiBuZXZlciBzZXQgZm9yIG1lbW9yeS10by1tZW1vcnkgcGlwZWxp bmVzLgo+ID4gKwkgKi8KPiA+ICsJdnNwMV9kbF9ib2R5X3dyaXRlKGRsYiwgVkk2X0RJU1BfSVJR X1NUQShpbmRleCksIDApOwo+ID4gKwlpZiAod3BmLT53cml0ZWJhY2spIHsKPiAKPiBJIGZlZWwg bGlrZSBhIGNvbW1lbnQgaGVyZSB3b3VsZCBiZSB1c2VmdWwgdG8gbWFrZSBpdCBjbGVhciB0aGF0 IGJ5Cj4gdXNpbmcgX3BhdGNoIHRoZSBWSTZfRElTUF9JUlFfRU5CX0RTVEUsIGFuZCBWSTZfV1BG X1dSQkNLX0NUUkxfV0JNRCB3aWxsCj4gYmUgcmVzZXQgdG8gMCBhdCB0aGUgZnJhbWUtZW5kPwo+ IAo+IEJ1dCBtYXliZSB0aGF0J3MgdG9vIHZlcmJvc2UgLi4uIGFuZCB3b24ndCBiZSBhbiBpc3N1 ZSBvbmNlIHRoZSBmdW5jdGlvbgo+IGRvY3VtZW50YXRpb24gaXMgdXBkYXRlZCBmb3IgdnNwMV9k bF9ib2R5X3dyaXRlX3BhdGNoKCkuCgpJJ2xsIGFkZCBhIGNvbW1lbnQuCgo+ID4gKwkJdnNwMV9k bF9ib2R5X3dyaXRlX3BhdGNoKGRsYiwgVkk2X0RJU1BfSVJRX0VOQihpbmRleCksCj4gPiArCQkJ CQkgVkk2X0RJU1BfSVJRX0VOQl9EU1RFLCAwKTsKPiA+ICsJCXZzcDFfZGxfYm9keV93cml0ZV9w YXRjaChkbGIsIFZJNl9XUEZfV1JCQ0tfQ1RSTChpbmRleCksCj4gPiArCQkJCQkgVkk2X1dQRl9X UkJDS19DVFJMX1dCTUQsIDApOwo+ID4gKwl9IGVsc2Ugewo+ID4gKwkJdnNwMV9kbF9ib2R5X3dy aXRlKGRsYiwgVkk2X0RJU1BfSVJRX0VOQihpbmRleCksIDApOwo+ID4gKwkJdnNwMV9kbF9ib2R5 X3dyaXRlKGRsYiwgVkk2X1dQRl9XUkJDS19DVFJMKGluZGV4KSwgMCk7Cj4gPiArCX0KPiA+ICB9 Cj4gPiAgCj4gPiAgc3RhdGljIHZvaWQgd3BmX2NvbmZpZ3VyZV9mcmFtZShzdHJ1Y3QgdnNwMV9l bnRpdHkgKmVudGl0eSwKPiA+IEBAIC0zOTAsNyArNDA0LDExIEBAIHN0YXRpYyB2b2lkIHdwZl9j b25maWd1cmVfcGFydGl0aW9uKHN0cnVjdCB2c3AxX2VudGl0eSAqZW50aXR5LAo+ID4gIAkJICAg ICAgICgwIDw8IFZJNl9XUEZfU1pDTElQX09GU1RfU0hJRlQpIHwKPiA+ICAJCSAgICAgICAoaGVp Z2h0IDw8IFZJNl9XUEZfU1pDTElQX1NJWkVfU0hJRlQpKTsKPiA+ICAKPiA+IC0JaWYgKHBpcGUt PmxpZikKPiA+ICsJLyoKPiA+ICsJICogRm9yIGRpc3BsYXkgcGlwZWxpbmVzIHdpdGhvdXQgd3Jp dGViYWNrIGVuYWJsZWQgdGhlcmUncyBubyBtZW1vcnkKPiA+ICsJICogYWRkcmVzcyB0byBjb25m aWd1cmUsIHJldHVybiBub3cuCj4gPiArCSAqLwo+ID4gKwlpZiAocGlwZS0+bGlmICYmICF3cGYt PndyaXRlYmFjaykKPiA+ICAJCXJldHVybjsKPiA+ICAKPiA+ICAJLyoKPiA+IEBAIC00NzksNiAr NDk3LDEyIEBAIHN0YXRpYyB2b2lkIHdwZl9jb25maWd1cmVfcGFydGl0aW9uKHN0cnVjdCB2c3Ax X2VudGl0eSAqZW50aXR5LAo+ID4gIAl2c3AxX3dwZl93cml0ZSh3cGYsIGRsYiwgVkk2X1dQRl9E U1RNX0FERFJfWSwgbWVtLmFkZHJbMF0pOwo+ID4gIAl2c3AxX3dwZl93cml0ZSh3cGYsIGRsYiwg Vkk2X1dQRl9EU1RNX0FERFJfQzAsIG1lbS5hZGRyWzFdKTsKPiA+ICAJdnNwMV93cGZfd3JpdGUo d3BmLCBkbGIsIFZJNl9XUEZfRFNUTV9BRERSX0MxLCBtZW0uYWRkclsyXSk7Cj4gPiArCj4gPiAr CS8qCj4gPiArCSAqIFdyaXRlYmFjayBvcGVyYXRlcyBpbiBzaW5nbGUtc2hvdCBtb2RlIGFuZCBs YXN0cyBmb3IgYSBzaW5nbGUgZnJhbWUsCj4gPiArCSAqIHJlc2V0IHRoZSB3cml0ZWJhY2sgZmxh ZyB0byBmYWxzZSBmb3IgdGhlIG5leHQgZnJhbWUuCj4gPiArCSAqLwo+ID4gKwl3cGYtPndyaXRl YmFjayA9IGZhbHNlOwo+IAo+IFRoaXMgZGlmZmVycyBmcm9tIG15IGltcGxlbWVudGF0aW9uIHJp Z2h0PyBJIHRoaW5rIG15IHZlcnNpb24ganVzdCByYW4KPiB3aGVuZXZlciB0aGVyZSB3YXMgYSBi dWZmZXIgYXZhaWxhYmxlLiAoRXhjZXB0IHRoYXQgd2hlbiB0aGVyZSB3YXMgbm8KPiBhdG9taWNf Zmx1c2ggLSB0aGVyZSB3YXMgYSBsYXJnZSBhbW91bnQgb2YgbGF0ZW5jeS4uLikKClllcywgaXQg ZGlmZmVycyBxdWl0ZSBhIGJpdC4KCj4gSSBndWVzcyB0aGlzIGNvbWVzIGRvd24gdG8gdGhlIGZh Y3QgdGhhdCB3ZSB3aWxsIG5vdCBxdWV1ZSB1cCBmcmFtZXMKPiBleGNlcHQgdW5sZXNzIHRoZXJl IGlzIGEgcmVhbCBmcmFtZS1jaGFuZ2UgY2F1c2VkIGJ5IGEgZnJlc2gKPiBhdG9taWNfZmx1c2gg Li4uIGFuZCBzbyB0aGUgYnVmZmVyIHJhdGUgZG9lcyBub3QgcmVmbGVjdCB0aGUgZGlzcGxheQo+ IHJlZnJlc2ggcmF0ZS4KCllvdSBjYW4gcXVldWUgYnVmZmVycyBhdCBhbnkgdGltZSBidXQgdGhl eSB3aWxsIG9ubHkgYmUgcHJvY2Vzc2VkIG9uIGFuCmF0b21pYyBjb21taXQuCgo+IE5vdyB0aGF0 IEkndmUgd3JpdHRlbiB0aGUgYWJvdmUsIEkgdGhpbmsgdGhhdCdzIG1hZGUgdGhlIHJlYXNvbmlu Zwo+IGNsZWFyZXIgZm9yIG1lIHNvIEkndmUgYW5zd2VyZWQgbXkgb3duIHF1ZXN0aW9ucyA6KQo+ IAo+ID4gIH0KPiA+ICAKPiA+ICBzdGF0aWMgdW5zaWduZWQgaW50IHdwZl9tYXhfd2lkdGgoc3Ry dWN0IHZzcDFfZW50aXR5ICplbnRpdHksCj4gPiBAQCAtNTI5LDYgKzU1MywxMyBAQCBzdHJ1Y3Qg dnNwMV9yd3BmICp2c3AxX3dwZl9jcmVhdGUoc3RydWN0IHZzcDFfZGV2aWNlICp2c3AxLCB1bnNp Z25lZCBpbnQgaW5kZXgpCj4gPiAgCQl3cGYtPm1heF9oZWlnaHQgPSBXUEZfR0VOM19NQVhfSEVJ R0hUOwo+ID4gIAl9Cj4gPiAgCj4gPiArCS8qCj4gPiArCSAqIE9uIEdlbjMgV1BGcyB3aXRoIGEg TElGIG91dHB1dCBjYW4gYWxzbyB3cml0ZSB0byBtZW1vcnkgZm9yIGRpc3BsYXkKPiAKPiBIcm0g Li4uIEkgbWlnaHQgaGF2ZSBzYWlkICd3aXRoIGFuIExJRicuIC4uLiBidXQgaXQgZGVwZW5kcyB3 aGV0aGVyIHlvdSBzYXk6Cj4gICAgJ3dpdGggYSBsaXBoJwo+IAo+IG9yIHlvdSBzcGVsbCBpdCBv dXQ6Cj4gCj4gICAgJ3dpdGggYW4gZWxsLWV5ZS1lZmYKPiAKPiBJIHBlcnNvbmFsbHkgc3BlbGwg b3V0IGFjcm9ueW1zIGluIG15IGhlYWQsIHNvIHRoYXQgbWFrZXMgaXMgJ2FuJy4KCkkgZG8gaXQg dGhlIG90aGVyIHdheSA6LSkKCj4gSXQgZG9lc24ndCBtYXR0ZXIgd2hpY2ggcmVhbGx5IGhlcmUg dGhvdWdoIDotKQo+IAo+ID4gKwkgKiB3cml0ZWJhY2suCj4gPiArCSAqLwo+ID4gKwlpZiAodnNw MS0+aW5mby0+Z2VuID4gMiAmJiBpbmRleCA8IHZzcDEtPmluZm8tPmxpZl9jb3VudCkKPiA+ICsJ CXdwZi0+aGFzX3dyaXRlYmFjayA9IHRydWU7Cj4gPiArCj4gPiAgCXdwZi0+ZW50aXR5Lm9wcyA9 ICZ3cGZfZW50aXR5X29wczsKPiA+ICAJd3BmLT5lbnRpdHkudHlwZSA9IFZTUDFfRU5USVRZX1dQ RjsKPiA+ICAJd3BmLT5lbnRpdHkuaW5kZXggPSBpbmRleDsKCi0tIApSZWdhcmRzLAoKTGF1cmVu dCBQaW5jaGFydApfX19fX19fX19fX19fX19fX19fX19fX19fX19fX19fX19fX19fX19fX19fX19f XwpkcmktZGV2ZWwgbWFpbGluZyBsaXN0CmRyaS1kZXZlbEBsaXN0cy5mcmVlZGVza3RvcC5vcmcK aHR0cHM6Ly9saXN0cy5mcmVlZGVza3RvcC5vcmcvbWFpbG1hbi9saXN0aW5mby9kcmktZGV2ZWw=