bmx-ng / brl.mod

BlitzMax Runtime Libraries, for BlitzMax NG.
12 stars 11 forks source link

Issues with 'library callbacks' with a potential solution #297

Open davecamp opened 1 year ago

davecamp commented 1 year ago

Hiya,

Problem: Some media (audio/video) libraries create their own threads which use a callback mechanism for the user to process data. Unfortunately these threads do not register themselves with anything related to BlitzMax. When the thread then calls back into the users BlitzMax code then some problems are encountered.

The problems are 2 fold.

  1. The thread is not registered with the GC causing any object management to cause issues when deallocated.
  2. For debug builds the debugger uses TLS to store debug frame related information so when the callback is entered in a debug build the debugger crashes because there is no valid TLS associated with thread.

Possible solution: Is it possible to use the metadata syntax to mark a callback function using something such as

Function SomeCallback(SomeData:Int) { callback }
EndFunction

?

If this could work then the compiler could potentially inject a function call at the beginning of a callback function. This 'internal' called function would verify if the 'current thread' is registered by scanning the list of 'static BBThread *threads' in blitz_threads.c. If the thread is not in the list then it could register itself accordingly (which would also set up TLS for a debug build) before any of the callback function code is run, including the debug data in the stack frame.

I understand this would have a very small impact on performance each time the callback is called because of looping through a list of thread pointers but I don't think this would be an issue compared to user code having orders of magnitude more complex code.

Do you have any thoughts on this? There is some rambling of mine in the discord server along with a previous conversation/issue of how this came all about: https://discord.com/channels/613699895139762176/679291789840089108/1151707238684176518

davecamp commented 1 year ago

@GWRon posted that a simple 'flag' at the beginning of the callback function to know if the registration of the thread has been checked/added would be a better solution as opposed to looping through the thread list.

davecamp commented 1 year ago

After further discussion the consensus is that GWRon suggestion will not work due to each thread being required to register itself. If more than 1 thread entered the callback function, the first thread would set the flag, the second thread would think it is registered causing the same initial problems.