Skip to content

Commit 978a521

Browse files
Merge pull request #11436 from Scavanger/SITL-Improvements
[SITL] Maintenance and Improvements
2 parents 606478a + bdf10e1 commit 978a521

File tree

12 files changed

+821
-334
lines changed

12 files changed

+821
-334
lines changed

cmake/main.cmake

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -108,10 +108,10 @@ function(setup_firmware_target exe name)
108108
endfunction()
109109

110110
function(exclude_from_all target)
111-
set_property(TARGET ${target} PROPERTY
111+
set_target_properties(${target} PROPERTIES
112112
TARGET_MESSAGES OFF
113-
EXCLUDE_FROM_ALL 1
114-
EXCLUDE_FROM_DEFAULT_BUILD 1)
113+
EXCLUDE_FROM_ALL ON
114+
EXCLUDE_FROM_DEFAULT_BUILD ON)
115115
endfunction()
116116

117117
function(collect_targets)

cmake/sitl.cmake

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -19,8 +19,8 @@ main_sources(SITL_SRC
1919
target/SITL/sim/realFlight.h
2020
target/SITL/sim/simHelper.c
2121
target/SITL/sim/simHelper.h
22-
target/SITL/sim/simple_soap_client.c
23-
target/SITL/sim/simple_soap_client.h
22+
target/SITL/sim/soap_client.c
23+
target/SITL/sim/soap_client.h
2424
target/SITL/sim/xplane.c
2525
target/SITL/sim/xplane.h
2626
)
@@ -163,8 +163,8 @@ function (target_sitl name)
163163
WORKING_DIRECTORY ${CMAKE_BINARY_DIR}
164164
COMMAND ${generator_cmd} clean
165165
COMMENT "Removing intermediate files for ${name}")
166-
set_property(TARGET ${clean_target} PROPERTY
167-
EXCLUDE_FROM_ALL 1
168-
EXCLUDE_FROM_DEFAULT_BUILD 1)
166+
set_target_properties(${clean_target} PROPERTIES
167+
EXCLUDE_FROM_ALL ON
168+
EXCLUDE_FROM_DEFAULT_BUILD ON)
169169
endif()
170170
endfunction()

src/main/config/config_streamer_file.c

Lines changed: 0 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -47,7 +47,6 @@ bool configFileSetPath(char* path)
4747
void config_streamer_impl_unlock(void)
4848
{
4949
if (eepromFd != NULL) {
50-
fprintf(stderr, "[EEPROM] Unable to load %s\n", eepromPath);
5150
return;
5251
}
5352

@@ -103,7 +102,6 @@ int config_streamer_impl_write_word(config_streamer_t *c, config_streamer_buffer
103102

104103
if ((c->address >= (uintptr_t)eepromData) && (c->address < (uintptr_t)ARRAYEND(eepromData))) {
105104
*((uint32_t*)c->address) = *buffer;
106-
fprintf(stderr, "[EEPROM] Program word %p = %08x\n", (void*)c->address, *((uint32_t*)c->address));
107105
} else {
108106
fprintf(stderr, "[EEPROM] Program word %p out of range!\n", (void*)c->address);
109107
}

src/main/scheduler/scheduler.c

Lines changed: 50 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -19,6 +19,10 @@
1919
#include <stdint.h>
2020
#include <string.h>
2121

22+
#if defined(SITL_BUILD)
23+
#include <unistd.h>
24+
#endif
25+
2226
#include "platform.h"
2327

2428
#include "scheduler.h"
@@ -215,11 +219,22 @@ void FAST_CODE NOINLINE scheduler(void)
215219
uint16_t selectedTaskDynamicPriority = 0;
216220
bool forcedRealTimeTask = false;
217221

222+
#if defined(SITL_BUILD)
223+
// Track the earliest time at which the next task will become due so we can
224+
// sleep until then instead of busy-waiting. Cap at 1 ms so event-driven
225+
// tasks (checkFunc) are still polled frequently enough.
226+
timeUs_t sitlEarliestNextTaskAt = currentTimeUs + 1000;
227+
bool sitlHasCheckFuncTask = false;
228+
#endif
229+
218230
// Update task dynamic priorities
219231
uint16_t waitingTasks = 0;
220232
for (cfTask_t *task = queueFirst(); task != NULL; task = queueNext()) {
221233
// Task has checkFunc - event driven
222234
if (task->checkFunc) {
235+
#if defined(SITL_BUILD)
236+
sitlHasCheckFuncTask = true;
237+
#endif
223238
const timeUs_t currentTimeBeforeCheckFuncCallUs = micros();
224239

225240
// Increase priority for event driven tasks
@@ -248,7 +263,19 @@ void FAST_CODE NOINLINE scheduler(void)
248263
waitingTasks++;
249264
forcedRealTimeTask = true;
250265
}
266+
#if defined(SITL_BUILD)
267+
const timeUs_t taskNextAt = task->lastExecutedAt + (timeUs_t)task->desiredPeriod;
268+
if (taskNextAt < sitlEarliestNextTaskAt) {
269+
sitlEarliestNextTaskAt = taskNextAt;
270+
}
271+
#endif
251272
} else {
273+
#if defined(SITL_BUILD)
274+
const timeUs_t taskNextAt = task->lastExecutedAt + (timeUs_t)task->desiredPeriod;
275+
if (taskNextAt < sitlEarliestNextTaskAt) {
276+
sitlEarliestNextTaskAt = taskNextAt;
277+
}
278+
#endif
252279
// Task is time-driven, dynamicPriority is last execution age (measured in desiredPeriods)
253280
// Task age is calculated from last execution
254281
task->taskAgeCycles = ((timeDelta_t)(currentTimeUs - task->lastExecutedAt)) / task->desiredPeriod;
@@ -294,4 +321,27 @@ void FAST_CODE NOINLINE scheduler(void)
294321
selectedTask->totalExecutionTime += taskExecutionTime; // time consumed by scheduler + task
295322
selectedTask->maxExecutionTime = MAX(selectedTask->maxExecutionTime, taskExecutionTime);
296323
}
324+
325+
#if defined(SITL_BUILD)
326+
{
327+
// Avoid busy-waiting and burning 100% CPU in SITL. After executing the
328+
// current task (or finding nothing to do), sleep until just before the
329+
// next task is due. For event-driven tasks (checkFunc) we limit the
330+
// sleep so the check function is still called frequently.
331+
if (sitlHasCheckFuncTask) {
332+
// Poll event-driven tasks at least every 500 µs
333+
const timeUs_t eventCap = micros() + 500;
334+
if (eventCap < sitlEarliestNextTaskAt) {
335+
sitlEarliestNextTaskAt = eventCap;
336+
}
337+
}
338+
const timeUs_t nowUs = micros();
339+
if (sitlEarliestNextTaskAt > nowUs + 50) {
340+
const timeDelta_t sleepUs = (timeDelta_t)(sitlEarliestNextTaskAt - nowUs) - 50;
341+
if (sleepUs > 0) {
342+
usleep((useconds_t)sleepUs);
343+
}
344+
}
345+
}
346+
#endif
297347
}

0 commit comments

Comments
 (0)