Skip to content

Commit 830ce74

Browse files
committed
extmod/modutimeq: Make scheduling fair (round-robin).
By adding back monotonically increasing field in addition to time field. As heapsort is not stable, without this, among entried added and readded at the same time instant, some might be always selected, and some might never be selected, leading to scheduling starvation.
1 parent bdd48e6 commit 830ce74

1 file changed

Lines changed: 9 additions & 1 deletion

File tree

extmod/modutimeq.c

Lines changed: 9 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -4,7 +4,7 @@
44
* The MIT License (MIT)
55
*
66
* Copyright (c) 2014 Damien P. George
7-
* Copyright (c) 2016 Paul Sokolovsky
7+
* Copyright (c) 2016-2017 Paul Sokolovsky
88
*
99
* Permission is hereby granted, free of charge, to any person obtaining a copy
1010
* of this software and associated documentation files (the "Software"), to deal
@@ -43,6 +43,7 @@
4343

4444
struct qentry {
4545
mp_uint_t time;
46+
mp_uint_t id;
4647
mp_obj_t callback;
4748
mp_obj_t args;
4849
};
@@ -54,6 +55,7 @@ typedef struct _mp_obj_utimeq_t {
5455
struct qentry items[];
5556
} mp_obj_utimeq_t;
5657

58+
STATIC mp_uint_t utimeq_id;
5759

5860
STATIC mp_obj_utimeq_t *get_heap(mp_obj_t heap_in) {
5961
return MP_OBJ_TO_PTR(heap_in);
@@ -63,6 +65,11 @@ STATIC bool time_less_than(struct qentry *item, struct qentry *parent) {
6365
mp_uint_t item_tm = item->time;
6466
mp_uint_t parent_tm = parent->time;
6567
mp_uint_t res = parent_tm - item_tm;
68+
if (res == 0) {
69+
// TODO: This actually should use the same "ring" logic
70+
// as for time, to avoid artifacts when id's overflow.
71+
return item->id < parent->id;
72+
}
6673
if ((mp_int_t)res < 0) {
6774
res += MODULO;
6875
}
@@ -125,6 +132,7 @@ STATIC mp_obj_t mod_utimeq_heappush(size_t n_args, const mp_obj_t *args) {
125132
}
126133
mp_uint_t l = heap->len;
127134
heap->items[l].time = MP_OBJ_SMALL_INT_VALUE(args[1]);
135+
heap->items[l].id = utimeq_id++;
128136
heap->items[l].callback = args[2];
129137
heap->items[l].args = args[3];
130138
heap_siftdown(heap, 0, heap->len);

0 commit comments

Comments
 (0)