Recycle thread IDs

I’m having trouble figuring out how to use the vex::thread constructor with a void * argument, without running out of thread IDs - I noticed that after t.get_id() increases past 129, it wraps around to -1, and the callback function doesn’t seem to execute. Is there any way to reclaim finished thread IDs?

Example code
#include "vex.h"

using namespace vex;

int x;

int *x_ptr = &x;

void foo(void * arg) {
  int i = (*(int*) arg)++;
  printf("foo %d\n", i);
}

thread t;

int main() {
  vexcodeInit();

  repeat(130) {
    // Calling destructor seems to not affect anything
    // t.~thread();
    t = thread(foo, x_ptr);
    printf("t foo thread id %ld\n", t.get_id());
    printf("t foo native handle %p\n", t.native_handle());

    task::sleep(10);
  }
}
Terminal output
t foo thread id 4
t foo native handle 0x3800100
foo 0
t foo thread id 5
t foo native handle 0x3800100
foo 1
t foo thread id 6
t foo native handle 0x3800100
foo 2
t foo thread id 7
t foo native handle 0x3800100
foo 3
t foo thread id 8
t foo native handle 0x3800100
foo 4
t foo thread id 9
t foo native handle 0x3800100
foo 5
t foo thread id 10
t foo native handle 0x3800100
foo 6
t foo thread id 11
t foo native handle 0x3800100
foo 7
t foo thread id 12
t foo native handle 0x3800100
foo 8
t foo thread id 13
t foo native handle 0x3800100
foo 9
t foo thread id 14
t foo native handle 0x3800100
foo 10
t foo thread id 15
t foo native handle 0x3800100
foo 11
t foo thread id 16
t foo native handle 0x3800100
foo 12
t foo thread id 17
t foo native handle 0x3800100
foo 13
t foo thread id 18
t foo native handle 0x3800100
foo 14
t foo thread id 19
t foo native handle 0x3800100
foo 15
t foo thread id 20
t foo native handle 0x3800100
foo 16
t foo thread id 21
t foo native handle 0x3800100
foo 17
t foo thread id 22
t foo native handle 0x3800100
foo 18
t foo thread id 23
t foo native handle 0x3800100
foo 19
t foo thread id 24
t foo native handle 0x3800100
foo 20
t foo thread id 25
t foo native handle 0x3800100
foo 21
t foo thread id 26
t foo native handle 0x3800100
foo 22
t foo thread id 27
t foo native handle 0x3800100
foo 23
t foo thread id 28
t foo native handle 0x3800100
foo 24
t foo thread id 29
t foo native handle 0x3800100
foo 25
t foo thread id 30
t foo native handle 0x3800100
foo 26
t foo thread id 31
t foo native handle 0x3800100
foo 27
t foo thread id 32
t foo native handle 0x3800100
foo 28
t foo thread id 33
t foo native handle 0x3800100
foo 29
t foo thread id 34
t foo native handle 0x3800100
foo 30
t foo thread id 35
t foo native handle 0x3800100
foo 31
t foo thread id 36
t foo native handle 0x3800100
foo 32
t foo thread id 37
t foo native handle 0x3800100
foo 33
t foo thread id 38
t foo native handle 0x3800100
foo 34
t foo thread id 39
t foo native handle 0x3800100
foo 35
t foo thread id 40
t foo native handle 0x3800100
foo 36
t foo thread id 41
t foo native handle 0x3800100
foo 37
t foo thread id 42
t foo native handle 0x3800100
foo 38
t foo thread id 43
t foo native handle 0x3800100
foo 39
t foo thread id 44
t foo native handle 0x3800100
foo 40
t foo thread id 45
t foo native handle 0x3800100
foo 41
t foo thread id 46
t foo native handle 0x3800100
foo 42
t foo thread id 47
t foo native handle 0x3800100
foo 43
t foo thread id 48
t foo native handle 0x3800100
foo 44
t foo thread id 49
t foo native handle 0x3800100
foo 45
t foo thread id 50
t foo native handle 0x3800100
foo 46
t foo thread id 51
t foo native handle 0x3800100
foo 47
t foo thread id 52
t foo native handle 0x3800100
foo 48
t foo thread id 53
t foo native handle 0x3800100
foo 49
t foo thread id 54
t foo native handle 0x3800100
foo 50
t foo thread id 55
t foo native handle 0x3800100
foo 51
t foo thread id 56
t foo native handle 0x3800100
foo 52
t foo thread id 57
t foo native handle 0x3800100
foo 53
t foo thread id 58
t foo native handle 0x3800100
foo 54
t foo thread id 59
t foo native handle 0x3800100
foo 55
t foo thread id 60
t foo native handle 0x3800100
foo 56
t foo thread id 61
t foo native handle 0x3800100
foo 57
t foo thread id 62
t foo native handle 0x3800100
foo 58
t foo thread id 63
t foo native handle 0x3800100
foo 59
t foo thread id 64
t foo native handle 0x3800100
foo 60
t foo thread id 65
t foo native handle 0x3800100
foo 61
t foo thread id 66
t foo native handle 0x3800100
foo 62
t foo thread id 67
t foo native handle 0x3800100
foo 63
t foo thread id 68
t foo native handle 0x3800100
foo 64
t foo thread id 69
t foo native handle 0x3800100
foo 65
t foo thread id 70
t foo native handle 0x3800100
foo 66
t foo thread id 71
t foo native handle 0x3800100
foo 67
t foo thread id 72
t foo native handle 0x3800100
foo 68
t foo thread id 73
t foo native handle 0x3800100
foo 69
t foo thread id 74
t foo native handle 0x3800100
foo 70
t foo thread id 75
t foo native handle 0x3800100
foo 71
t foo thread id 76
t foo native handle 0x3800100
foo 72
t foo thread id 77
t foo native handle 0x3800100
foo 73
t foo thread id 78
t foo native handle 0x3800100
foo 74
t foo thread id 79
t foo native handle 0x3800100
foo 75
t foo thread id 80
t foo native handle 0x3800100
foo 76
t foo thread id 81
t foo native handle 0x3800100
foo 77
t foo thread id 82
t foo native handle 0x3800100
foo 78
t foo thread id 83
t foo native handle 0x3800100
foo 79
t foo thread id 84
t foo native handle 0x3800100
foo 80
t foo thread id 85
t foo native handle 0x3800100
foo 81
t foo thread id 86
t foo native handle 0x3800100
foo 82
t foo thread id 87
t foo native handle 0x3800100
foo 83
t foo thread id 88
t foo native handle 0x3800100
foo 84
t foo thread id 89
t foo native handle 0x3800100
foo 85
t foo thread id 90
t foo native handle 0x3800100
foo 86
t foo thread id 91
t foo native handle 0x3800100
foo 87
t foo thread id 92
t foo native handle 0x3800100
foo 88
t foo thread id 93
t foo native handle 0x3800100
foo 89
t foo thread id 94
t foo native handle 0x3800100
foo 90
t foo thread id 95
t foo native handle 0x3800100
foo 91
t foo thread id 96
t foo native handle 0x3800100
foo 92
t foo thread id 97
t foo native handle 0x3800100
foo 93
t foo thread id 98
t foo native handle 0x3800100
foo 94
t foo thread id 99
t foo native handle 0x3800100
foo 95
t foo thread id 100
t foo native handle 0x3800100
foo 96
t foo thread id 101
t foo native handle 0x3800100
foo 97
t foo thread id 102
t foo native handle 0x3800100
foo 98
t foo thread id 103
t foo native handle 0x3800100
foo 99
t foo thread id 104
t foo native handle 0x3800100
foo 100
t foo thread id 105
t foo native handle 0x3800100
foo 101
t foo thread id 106
t foo native handle 0x3800100
foo 102
t foo thread id 107
t foo native handle 0x3800100
foo 103
t foo thread id 108
t foo native handle 0x3800100
foo 104
t foo thread id 109
t foo native handle 0x3800100
foo 105
t foo thread id 110
t foo native handle 0x3800100
foo 106
t foo thread id 111
t foo native handle 0x3800100
foo 107
t foo thread id 112
t foo native handle 0x3800100
foo 108
t foo thread id 113
t foo native handle 0x3800100
foo 109
t foo thread id 114
t foo native handle 0x3800100
foo 110
t foo thread id 115
t foo native handle 0x3800100
foo 111
t foo thread id 116
t foo native handle 0x3800100
foo 112
t foo thread id 117
t foo native handle 0x3800100
foo 113
t foo thread id 118
t foo native handle 0x3800100
foo 114
t foo thread id 119
t foo native handle 0x3800100
foo 115
t foo thread id 120
t foo native handle 0x3800100
foo 116
t foo thread id 121
t foo native handle 0x3800100
foo 117
t foo thread id 122
t foo native handle 0x3800100
foo 118
t foo thread id 123
t foo native handle 0x3800100
foo 119
t foo thread id 124
t foo native handle 0x3800100
foo 120
t foo thread id 125
t foo native handle 0x3800100
foo 121
t foo thread id 126
t foo native handle 0x3800100
foo 122
t foo thread id 127
t foo native handle 0x3800100
foo 123
t foo thread id 128
t foo native handle 0x3800100
foo 124
t foo thread id 129
t foo native handle 0x3800100
foo 125
t foo thread id -1
t foo native handle 0x3800100
t foo thread id -1
t foo native handle 0x3800100
t foo thread id -1
t foo native handle 0x3800100
t foo thread id -1
t foo native handle 0x3800100

yea, you can’t with the current scheduler (In the future this will be allowed, I had to add some functionality for the upcoming Python VM), and if you are needing to constantly create new threads with arguments, you are probably using them wrong, perhaps you really just need a function.

What are you trying to achieve ?

3 Likes

Ah ok, thanks. I’m trying to make my own button callback system that only runs a function if no other function in its group is running (for example to prevent two conflicting macros from running simultaneously). I’ve gotten it to work if I don’t pass in a void * argument in the constructor, but then I think the threads can link together in weird ways in certain edge cases. Here’s an example where I can stop a function running on a separate thread unless I reassign the first thread to a different function:

Code
#include "vex.h"

using namespace vex;

void func1() {
  printf("start func1\n");
    int count = 0;

  repeat(5) {
    printf("func1 %d\n", count++);
    
    // don't hog the cpu :)
    wait(1, sec);
  }
  printf("end func1\n");
}

void func2() {
  printf("func2\n");
}

thread a;
thread b;

int main() {
  vexcodeInit();

  a = thread(func1);
  wait(6, sec);

  b = thread(func1);
  wait(2, sec);
  a.interrupt();
  printf("a.interrupt()\n");


  printf("\n=========\n");
  a = thread(func1);
  wait(6, sec);

  a = thread(func2); // Reasign thread "a"
  wait(1, sec);

  b = thread(func1);
  wait(2, sec);
  a.interrupt();
  printf("a.interrupt()\n");
}
Terminal output
start func1
func1 0
func1 1
func1 2
func1 3
func1 4
end func1
start func1
func1 0
func1 1
a.interrupt()

=========
start func1
func1 0
func1 1
func1 2
func1 3
func1 4
end func1
func2
start func1
func1 0
func1 1
a.interrupt()
func1 2
func1 3
func1 4
end func1

I know that most of the time this won’t be an issue, but I can think a few situations where I would want to have the same macro start on separate threads triggered by separate buttons (an example would be if you release a certain button on the primary controller, it stops a macro but only if it was started from the primary controller)