前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >并发中的同步--WCF并发体系的同步机制实现

并发中的同步--WCF并发体系的同步机制实现

作者头像
蒋金楠
发布2018-01-16 17:31:43
8390
发布2018-01-16 17:31:43
举报
文章被收录于专栏:大内老A

在《WCF 并发的本质》中,我们谈到了WCF提供的三种不同的并发模式,使开发者可以根据具体的情况选择不同的并发处理的策略。对于这三种并发模式,Multiple采用的并行的执行方式,而Single和Reentrant则是采用串行的执行方式。串行执行即同步执行,在WCF并发框架体系中,这样的同步机制是如何实现的呢?

一、Concurrency.Single模式下的同步实现

实际上,WCF并发框架体系下针对Concurrency.Single模式的实现非常简单,其本质就是对InstanceContext进行加锁。如果采用反编译工具查看InstanceContext的定义,你会发现InstanceContext类中定义了一个类型为System.Object名为ThisLock的内部属性,而该属性实际上就是对基类CommunicationObject同名属性的引用,相关代码入下所示。WCF就是通过对InstanceContext的ThisLock进行加锁,确保了对InstanceContext的同步访问。

代码语言:js
复制
   1: public sealed class InstanceContext : CommunicationObject, IExtensibleObject<InstanceContext>
   2: {
   3:     //其它成员
   4:     internal object ThisLock
   5:     {
   6:         get
   7:         {
   8:             return base.ThisLock;
   9:         }
  10:     }
  11: }
  12: public abstract class CommunicationObject : ICommunicationObject
  13: {
  14:     //其它成员
  15:     protected object ThisLock { get; }
  16: }

具体来讲,WCF服务端运行时在处理服务调用消息请求之后,利用实例上下文提供者(InstanceContextProvider)创建新的或者获取现有的InstanceContext。然后,WCF会将请求消息分发给该InstanceContext对消息进行进一步处理。在处理操作执行之前,如果发现相应的服务采用的并发模式是ConcurrencyMode.Single,WCF运行时会试图获取InstanceContext的ThisLock上的锁,或者说后续的操作进行再对InstanceContext的ThisLock锁定的情况下执行的。这样就保证了单一的InstanceContext对象在ConcurrencyMode.Single并发模式下永远是以同步的方式被调用的。

二、Concurrency.Reentrant模式下的同步实现

在ConcurrencyMode.Single并发模式下,从请求被WCF服务端运行时分发给相应的InstanceContext到请求处理完成的整个过程中,InstanceContext被锁定。如果在服务操作执行过程中涉及到对客户端的回调,并且回调操作采用请求/回复消息交换模式,当被WCF服务端运行时接收到从客户端返回的回复消息后,会将请求消息再次分发给相同的InstanceContext。运行时分发回调回复消息与普通服务调用请求消息采用相同的机制,同样需要在对InstanceContext成功锁定的情况下进行。很明显,这样产生了死锁(Deadlock)。

所以,如果在服务操作执行过程中需要对客户端实施回调,要么将采用单向(One-way)的方式进行回调,要么将服务的并发模式设置成ConcurrencyMode.Reentrant或者ConcurrencyMode.Multiple。否则,如图1所示的InvalidOperationException异常会在进行回调操作的时候抛出。从异常消息我们可以看出,VS的汉化真的不敢恭维,如果要正常理解异常消息的含义,你需要知道这里的“邮件”、“可重输入”和“多个”是依次对“Message”、“Reentrant”和“Multiple”的翻译。

图1 在Single模式执行回调导致的异常

如果我们真的需要在服务操作过程中实施基于请求/回复模式的回调,毫无疑问采用Concurrency.Multiple并发模式可以解决死锁的问题,因为Concurrency.Multiple模式根本就是存在对InstanceContext加锁的问题。那么,在Concurrency.Reentrant模式下,WCF并发框架体系又是如何解决这个问题的呢?

Reentrant,翻译成汉语就是“重入”(VS将其翻译成“重输入”简直莫名其妙),意思是服务操作过程中完成了对外调用(Call Out)还能重新回到相应的位置继续执行。同Concurrency.Single模式一样,WCF运行时将调用请求消息分发给相应的InstanceContext之前,会先对其加锁。但是,在开始实施回调的之前,对InstanceContext的锁定会被解除,当回调返回后再对其加锁。

对于Concurrency.Reentrant有一点需要特别说明,当服务端进行回调时,由于加载InstanceContext上的锁会被释放,意味着其它服务请求会被分发给该InstanceContext。当回调返回的时候,如果InstanceContext正被用于才处理在进行回调过程抵达的请求,虽然自己是先来者,依然会等待,因为重入后的InstanceContext被锁定。如果等待的时间超过设定的超时时限,客户端会抛出TimeoutException异常。

由于WCF的并发是针对某个封装了服务实例的InstanceContext而言的,所以在不同的实例上下文模式下,会表现出不同的并发行为。在下一篇文章中,我将从具体的实例上下文模式的角度来剖析WCF的并发,敬请期待。

本文参与 腾讯云自媒体同步曝光计划,分享自作者个人站点/博客。
原始发表:2010-03-21 ,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 作者个人站点/博客 前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • 一、Concurrency.Single模式下的同步实现
  • 二、Concurrency.Reentrant模式下的同步实现
相关产品与服务
数据库
云数据库为企业提供了完善的关系型数据库、非关系型数据库、分析型数据库和数据库生态工具。您可以通过产品选择和组合搭建,轻松实现高可靠、高可用性、高性能等数据库需求。云数据库服务也可大幅减少您的运维工作量,更专注于业务发展,让企业一站式享受数据上云及分布式架构的技术红利!
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档