Adaptive AUTOSAR CM模块介绍(六)

Event订阅和缓存原理
Event事件并不是proxy定义了就可以使用,需要Event事件的订阅,一旦订阅成功了,有event事件的时候,就会收到订阅的消息。

/*
brief The application expects the CM to subscribe the event.
param maxSampleCount maximum number of samples,which can be held. 
*/
 void Subscribe(size_t maxSampleCount);

此方法需要一个参数maxSampleCount,它通过通信管理实现的订阅实现,定义了事件的最大值。因此,通过调用此方法,不仅可以告诉通信管理,现在有兴趣接收事件,而且还可以为那些绑定到具有给定最大SampleCount的事件包装器实例的事件设置“本地缓存”。
这个实现是给予一个本地缓存智能指针,Subcribe()是通过异步调用实现的,因此在调用这个事件的时候,如果正在进行调用的话,会发生pending.
查看订阅状态的函数为:

ara::com::SubscriptionState GetSubscriptionState()const

如果此时订阅后立即调用GetSubscriptionState可能会返回kSubscriptionPending的状态。如果成功的话,就会返回kSubscribed。

/**
*brief Get new data from the Communication Management 
*buffers and provide it in callbacks to the given callable f. 
.... 
*/
 template<typename F>
 ara::core::Result<size_t>GetNewSamples(  F&&f,
 size_t maxNumberOfSamples=std::numeric_limits<size_t>::max());

从服务端发送到订阅proxy实例的数据是通过IPC实现的,例如,内核缓冲区、特殊的IPC实现控制的共享内存区域等。因此,必须采取调用的操作,从这些缓冲区获取/获取这些事件,最终取消序列化,然后以正确的SampleType的形式将它们放入事件包装类实例特定的缓存中。
size_t类型的第二个参数控制事件样本的最大数量,这些样本将从中间件缓冲区中提取/反序列化,然后以函数调用f的形式呈现给应用程序。

在调用GetNewSamples()时,ara::com实现首先检查应用程序持有的事件样本数是否已经超过了它在上次调用Subscribe()时提交的最大数量。如果是,则返回一个ara::core::ErrorCode。否则,ara::com实现检查底层缓冲区是否包含一个新的事件样本,如果是这样的话,将其取消划分到一个样本槽中,然后调用f提供的应用程序,该应用程序具有指向该新事件样本的SamplePtr。重复此处理(检查缓冲区中的其他样本并回调应用程序提供的回调f)一直到新样本没有了,或者达到最大的数量。

以上是AP的事件的内部实现方式,但是从ara::com实现移交给用户层的是SamplePtr,它是一个唯一的指针(非常类似于std::unique_ptr),这个指针指向事件的内存池在IPC缓存中,一般是share memory。