2222#include " Framework/ControlService.h"
2323#include " Framework/SourceInfoHeader.h"
2424#include " Framework/ConfigParamRegistry.h"
25+ #include " Framework/RunningWorkflowInfo.h"
2526#include " Headers/DataHeader.h"
2627#include " Headers/Stack.h"
2728
3031
3132#include < fairmq/FairMQParts.h>
3233#include < fairmq/FairMQDevice.h>
34+ #include < fairmq/shmem/Monitor.h>
3335#include < cstring>
3436#include < cassert>
3537#include < memory>
@@ -347,7 +349,8 @@ DataProcessorSpec specifyExternalFairMQDeviceProxy(char const* name,
347349 std::function<void (FairMQDevice&,
348350 FairMQParts&,
349351 ChannelRetriever)>
350- converter)
352+ converter,
353+ uint64_t minSHM)
351354{
352355 DataProcessorSpec spec;
353356 spec.name = strdup (name);
@@ -356,7 +359,7 @@ DataProcessorSpec specifyExternalFairMQDeviceProxy(char const* name,
356359 // The Init method will register a new "Out of band" channel and
357360 // attach an OnData to it which is responsible for converting incoming
358361 // messages into DPL messages.
359- spec.algorithm = AlgorithmSpec{[converter, channel = spec.name ](InitContext& ctx) {
362+ spec.algorithm = AlgorithmSpec{[converter, channel = spec.name , minSHM ](InitContext& ctx) {
360363 auto device = ctx.services ().get <RawDeviceService>().device ();
361364 // make a copy of the output routes and pass to the lambda by move
362365 auto outputRoutes = ctx.services ().get <RawDeviceService>().spec ().outputs ;
@@ -411,7 +414,7 @@ DataProcessorSpec specifyExternalFairMQDeviceProxy(char const* name,
411414 }
412415 };
413416
414- auto runHandler = [dataHandler, device, channel](ProcessingContext& ctx) {
417+ auto runHandler = [dataHandler, device, channel, minSHM ](ProcessingContext& ctx) {
415418 static int64_t consumedTimeframes = 0 ;
416419 static int64_t sentTimeframes = 0 ;
417420 auto device = ctx.services ().get <RawDeviceService>().device ();
@@ -439,6 +442,23 @@ DataProcessorSpec specifyExternalFairMQDeviceProxy(char const* name,
439442 LOG (important) << (sentTimeframes - consumedTimeframes) << " / " << maxTFInFlight << " TF in flight, continuing to publish" ;
440443 }
441444 }
445+ if (minSHM) {
446+ int waitMessage = 0 ;
447+ auto & runningWorkflow = ctx.services ().get <RunningWorkflowInfo const >();
448+ while (true ) {
449+ uint64_t freeSHM = fair::mq::shmem::Monitor::GetFreeMemory (fair::mq::shmem::SessionId{device->fConfig ->GetProperty <std::string>(" session" )}, runningWorkflow.shmSegmentId );
450+ if (freeSHM > minSHM) {
451+ if (waitMessage) {
452+ LOG (important) << " Sufficient SHM memory free (" << freeSHM << " >= " << minSHM << " ), continuing to publish" ;
453+ }
454+ break ;
455+ }
456+ if (waitMessage == 0 ) {
457+ LOG (alarm) << " Free SHM memory too low: " << freeSHM << " < " << minSHM << " , waiting" ;
458+ waitMessage = 1 ;
459+ }
460+ }
461+ }
442462
443463 FairMQParts parts;
444464 device->Receive (parts, channel, 0 );
0 commit comments