在没有手动同步的情况下使用异步 API 更改反应器的状态是否安全?
Is it safe to change the reactor's state using the async API without manual synchronization?
嗨
我将 gRPC 与异步 API 结合使用。这需要基于 类 构建反应堆,例如 ClientBidiReactor or ServerBidiReactor
如果我理解正确的话,gRPC 是这样工作的:它从某个线程池中获取线程,并使用这些线程执行正在使用的反应堆的某些方法。
问题
现在,问题是反应器何时变为有状态。我知道单个反应器的方法很可能会按顺序执行,但它们可能 运行 来自不同的线程,这是正确的吗?如果是这样,那么我们是否可能遇到描述的问题,例如 here?
长话短说,如果我们在这种情况下有一个不同步的状态,是否有可能一个线程会更新状态,然后来自反应堆的下一个方法将从另一个线程执行,它会看到不-updated value 因为状态的新值还没有刷新到主内存?
老实说,我对此有点困惑。在 grpc 示例中 here and here 这似乎没有得到解决(互斥体在那里用于不同的目的并且值不是原子的)。
我 used/linked 比迪反应器的示例,但这指的是所有类型的反应器。
结论/问题
此时我基本上有几个问题:
- 这里的担忧是否有效,我是否正确理解了一切,还是我错过了什么?问题是否存在?
- 我们是否需要手动同步 reactors 的状态,或者它是由库以某种方式处理的(我的意思是刷新到处理过的主内存)?
- 图书馆作者是否意识到这一点?他们在编码我链接的示例时是否牢记这一点?
提前感谢您的帮助,祝一切顺利!
你是对的,这些例子并没有很好地展示这一点,还有一些改进的余地。 operation-completion 反应方法(OnReadInitialMetadataDone
、OnReadDone
、OnWriteDone
、...)可以从 gRPC 库拥有的不同线程同时调用,因此如果您的代码访问任何共享状态,您需要自己协调(通过同步、lock-free 类型等)。实际上,我不确定它发生的频率,或者哪些回调更有可能重叠。
原始回调 API 规范在“线程安全”条款下对此做了更多说明:例如 L67: C++ callback-based asynchronous API. The same is reiterated a few places in the callback implementation code itself - client_callback.h#L234-236。
嗨
我将 gRPC 与异步 API 结合使用。这需要基于 类 构建反应堆,例如 ClientBidiReactor or ServerBidiReactor
如果我理解正确的话,gRPC 是这样工作的:它从某个线程池中获取线程,并使用这些线程执行正在使用的反应堆的某些方法。
问题
现在,问题是反应器何时变为有状态。我知道单个反应器的方法很可能会按顺序执行,但它们可能 运行 来自不同的线程,这是正确的吗?如果是这样,那么我们是否可能遇到描述的问题,例如 here?
长话短说,如果我们在这种情况下有一个不同步的状态,是否有可能一个线程会更新状态,然后来自反应堆的下一个方法将从另一个线程执行,它会看到不-updated value 因为状态的新值还没有刷新到主内存?
老实说,我对此有点困惑。在 grpc 示例中 here and here 这似乎没有得到解决(互斥体在那里用于不同的目的并且值不是原子的)。
我 used/linked 比迪反应器的示例,但这指的是所有类型的反应器。
结论/问题
此时我基本上有几个问题:
- 这里的担忧是否有效,我是否正确理解了一切,还是我错过了什么?问题是否存在?
- 我们是否需要手动同步 reactors 的状态,或者它是由库以某种方式处理的(我的意思是刷新到处理过的主内存)?
- 图书馆作者是否意识到这一点?他们在编码我链接的示例时是否牢记这一点?
提前感谢您的帮助,祝一切顺利!
你是对的,这些例子并没有很好地展示这一点,还有一些改进的余地。 operation-completion 反应方法(OnReadInitialMetadataDone
、OnReadDone
、OnWriteDone
、...)可以从 gRPC 库拥有的不同线程同时调用,因此如果您的代码访问任何共享状态,您需要自己协调(通过同步、lock-free 类型等)。实际上,我不确定它发生的频率,或者哪些回调更有可能重叠。
原始回调 API 规范在“线程安全”条款下对此做了更多说明:例如 L67: C++ callback-based asynchronous API. The same is reiterated a few places in the callback implementation code itself - client_callback.h#L234-236。