Skip to content

Commit 40e390e

Browse files
committed
Add option to register only selected shm segment IDs on the GPU, to speed up workflow startup
1 parent 1d038c0 commit 40e390e

3 files changed

Lines changed: 41 additions & 32 deletions

File tree

GPU/GPUTracking/Definitions/GPUSettingsList.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -416,6 +416,7 @@ AddOption(mutexMemReg, bool, false, "", 0, "Global mutex to serialize GPU memory
416416
AddOption(printSettings, int, 0, "", 0, "Print all settings", def(1))
417417
AddOption(gpuDisplayfilterMacro, std::string, "", "", 0, "File name of ROOT macro for GPU display filter")
418418
AddOption(benchmarkMemoryRegistration, bool, false, "", 0, "Time-benchmark for memory registration")
419+
AddOption(registerSelectedSegmentIds, int, -1, "", 0, "Register only a specific managed shm segment id (-1 = all)")
419420
EndConfig()
420421
#endif // GPUCA_O2_LIB
421422
#endif // !GPUCA_GPUCODE_DEVICE

GPU/Workflow/src/GPUWorkflowSpec.cxx

Lines changed: 33 additions & 29 deletions
Original file line numberDiff line numberDiff line change
@@ -309,38 +309,42 @@ DataProcessorSpec getGPURecoWorkflowSpec(gpuworkflow::CompletionPolicyData* poli
309309

310310
auto& callbacks = ic.services().get<CallbackService>();
311311
callbacks.set(CallbackService::Id::RegionInfoCallback, [&processAttributes, confParam](FairMQRegionInfo const& info) {
312-
if (info.size) {
313-
int fd = 0;
314-
if (confParam.mutexMemReg) {
315-
mode_t mask = S_IRUSR | S_IWUSR | S_IRGRP | S_IWGRP | S_IROTH | S_IWOTH;
316-
fd = open("/tmp/o2_gpu_memlock_mutex.lock", O_RDWR | O_CREAT | O_CLOEXEC, mask);
317-
if (fd == -1) {
318-
throw std::runtime_error("Error opening lock file");
319-
}
320-
fchmod(fd, mask);
321-
if (lockf(fd, F_LOCK, 0)) {
322-
throw std::runtime_error("Error locking file");
323-
}
324-
}
325-
auto& tracker = processAttributes->tracker;
326-
std::chrono::time_point<std::chrono::high_resolution_clock> start, end;
327-
if (confParam.benchmarkMemoryRegistration) {
328-
start = std::chrono::high_resolution_clock::now();
329-
}
330-
if (tracker->registerMemoryForGPU(info.ptr, info.size)) {
331-
throw std::runtime_error("Error registering memory for GPU");
312+
if (info.size == 0) {
313+
return;
314+
}
315+
if (confParam.registerSelectedSegmentIds != -1 && info.managed && info.id != confParam.registerSelectedSegmentIds) {
316+
return;
317+
}
318+
int fd = 0;
319+
if (confParam.mutexMemReg) {
320+
mode_t mask = S_IRUSR | S_IWUSR | S_IRGRP | S_IWGRP | S_IROTH | S_IWOTH;
321+
fd = open("/tmp/o2_gpu_memlock_mutex.lock", O_RDWR | O_CREAT | O_CLOEXEC, mask);
322+
if (fd == -1) {
323+
throw std::runtime_error("Error opening lock file");
332324
}
333-
if (confParam.benchmarkMemoryRegistration) {
334-
end = std::chrono::high_resolution_clock::now();
335-
std::chrono::duration<double> elapsed_seconds = end - start;
336-
LOG(info) << "Memory registration time (0x" << info.ptr << ", " << info.size << " bytes): " << elapsed_seconds.count() << " s";
325+
fchmod(fd, mask);
326+
if (lockf(fd, F_LOCK, 0)) {
327+
throw std::runtime_error("Error locking file");
337328
}
338-
if (confParam.mutexMemReg) {
339-
if (lockf(fd, F_ULOCK, 0)) {
340-
throw std::runtime_error("Error unlocking file");
341-
}
342-
close(fd);
329+
}
330+
auto& tracker = processAttributes->tracker;
331+
std::chrono::time_point<std::chrono::high_resolution_clock> start, end;
332+
if (confParam.benchmarkMemoryRegistration) {
333+
start = std::chrono::high_resolution_clock::now();
334+
}
335+
if (tracker->registerMemoryForGPU(info.ptr, info.size)) {
336+
throw std::runtime_error("Error registering memory for GPU");
337+
}
338+
if (confParam.benchmarkMemoryRegistration) {
339+
end = std::chrono::high_resolution_clock::now();
340+
std::chrono::duration<double> elapsed_seconds = end - start;
341+
LOG(info) << "Memory registration time (0x" << info.ptr << ", " << info.size << " bytes): " << elapsed_seconds.count() << " s";
342+
}
343+
if (confParam.mutexMemReg) {
344+
if (lockf(fd, F_ULOCK, 0)) {
345+
throw std::runtime_error("Error unlocking file");
343346
}
347+
close(fd);
344348
}
345349
});
346350

prodtests/full-system-test/dpl-workflow.sh

Lines changed: 7 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -74,7 +74,7 @@ if [[ $EPNSYNCMODE == 1 ]]; then
7474
elif [[ "0$ENABLE_METRICS" != "01" ]]; then
7575
ARGS_ALL+=" --monitoring-backend no-op://"
7676
fi
77-
( [[ $EXTINPUT == 1 ]] || [[ $NUMAGPUIDS == 1 ]] ) && ARGS_ALL+=" --no-cleanup"
77+
( [[ $EXTINPUT == 1 ]] || [[ $NUMAGPUIDS != 0 ]] ) && ARGS_ALL+=" --no-cleanup"
7878
( [[ $GPUTYPE != "CPU" ]] || [[ $OPTIMIZED_PARALLEL_ASYNC != 0 ]] ) && ARGS_ALL+=" --shm-mlock-segment-on-creation 1"
7979
[[ $SHMTHROW == 0 ]] && ARGS_ALL+=" --shm-throw-bad-alloc 0"
8080
[[ $NORATELOG == 1 ]] && ARGS_ALL+=" --fairmq-rate-logging 0"
@@ -149,6 +149,10 @@ if [[ $EPNSYNCMODE == 1 ]]; then
149149
if [[ $EXTINPUT == 1 ]] && [[ $GPUTYPE != "CPU" ]] && [[ -z "$GPU_NUM_MEM_REG_CALLBACKS" ]]; then GPU_NUM_MEM_REG_CALLBACKS=4; fi
150150
fi
151151

152+
if [[ $GPUTYPE != "CPU" && $NUMAGPUIDS != 0 ]]; then
153+
GPU_CONFIG_KEY+="GPU_global.registerSelectedSegmentIds=$NUMAID;"
154+
fi
155+
152156
if [[ $GPUTYPE == "HIP" ]]; then
153157
if [[ $NUMAID == 0 ]] || [[ $NUMAGPUIDS == 0 ]]; then
154158
export TIMESLICEOFFSET=0
@@ -237,7 +241,7 @@ N_TPCTRK=$NGPUS
237241
if [[ $OPTIMIZED_PARALLEL_ASYNC != 0 ]]; then
238242
# Tuned multiplicities for async Pb-Pb processing
239243
if [[ $SYNCMODE == "1" ]]; then echo "Must not use OPTIMIZED_PARALLEL_ASYNC with GPU or SYNCMODE" 1>&2; exit 1; fi
240-
if [[ $NUMAGPUIDS == 1 ]]; then N_NUMAFACTOR=1; else N_NUMAFACTOR=2; fi
244+
if [[ $NUMAGPUIDS != 0 ]]; then N_NUMAFACTOR=1; else N_NUMAFACTOR=2; fi
241245
GPU_CONFIG_KEY+="GPU_proc.ompThreads=6;"
242246
TRD_CONFIG_KEY+="GPU_proc.ompThreads=2;"
243247
if [[ $GPUTYPE == "CPU" ]]; then
@@ -271,7 +275,7 @@ elif [[ $EPNPIPELINES != 0 ]]; then
271275
GPU_CONFIG_KEY+="GPU_proc.ompThreads=4;"
272276
fi
273277
# Scale some multiplicities with the number of nodes
274-
RECO_NUM_NODES_WORKFLOW_CMP=$((($RECO_NUM_NODES_WORKFLOW > 15 ? $RECO_NUM_NODES_WORKFLOW : 15) * ($NUMAGPUIDS == 1 ? 2 : 1))) # Limit the lower scaling factor, multiply by 2 if we have 2 NUMA domains
278+
RECO_NUM_NODES_WORKFLOW_CMP=$((($RECO_NUM_NODES_WORKFLOW > 15 ? $RECO_NUM_NODES_WORKFLOW : 15) * ($NUMAGPUIDS != 0 ? 2 : 1))) # Limit the lower scaling factor, multiply by 2 if we have 2 NUMA domains
275279
N_ITSRAWDEC=$(math_max $((3 * 60 / $RECO_NUM_NODES_WORKFLOW_CMP)) ${N_ITSRAWDEC:-1}) # This means, if we have 60 EPN nodes, we need at least 3 ITS RAW decoders
276280
N_MFTRAWDEC=$(math_max $((3 * 60 / $RECO_NUM_NODES_WORKFLOW_CMP)) ${N_MFTRAWDEC:-1})
277281
N_ITSTRK=$(math_max $((1 * 200 / $RECO_NUM_NODES_WORKFLOW_CMP)) ${N_ITSTRK:-1})

0 commit comments

Comments
 (0)