Keywords: STATUS_ACCESS_VIOLATION AudioContext AudioWorkletNode audioWorklet addModule resume suspended createScriptProcessor
crash Chrome test page: test page address
Article directory
cause of the incident
My GitHub open source front-end H5 recording library a few years ago: https://github.com/xiangyuecn/Recorder , provides mp3 wav ogg webm amr format support, has rich audio visualization, variable speed and pitch processing, audio stream playback, ASR voice Supporting functions such as identification; with powerful real-time processing support, it can be used in various web applications; recently, I plan to try to use new browser features to upgrade and follow the development of the previous era.
I don't remember which version of Chrome started, when the correct AudioContext
method createScriptProcessor
is called, it will print a method outdated reminder in the console: [Deprecation] The ScriptProcessorNode is deprecated. Use AudioWorkletNode instead.
.
ScriptProcessor
Although it is marked as obsolete, all modern browsers including early browsers are well supported and have not been officially removed on any browser. Chrome's outdated reminders have caused frequent Some people asked if they should use AudioWorklet
it instead. The current conclusion is that it is not necessary, because in terms of the scene of obtaining recording data, there is no difference in performance between the two on the PC side, but on the contrary, it has ScriptProcessor
more performance advantages on the mobile side. This is of course a later story.
In fact, I wanted to upgrade AudioWorklet
the support provided a long time ago. After simply going through the document, the expected increase in the amount of code will not be very large (in the end, 2KB was actually added after the actual compression. Check out the 100 lines of code here ), but drag It was only a while ago that I wrote the code.
Phenomenon recurrence
In the process of writing a good test at the beginning, I found that as long as the interactive operation is fast enough, the Chrome (version: 97) browser often crashes inexplicably (a phenomenon that has never been seen before), and the old version of Chrome80 will also crash, the error code: , STATUS_ACCESS_VIOLATION
more The old 66 and 70 did not crash (thanks to the " Making a Chrome Portable Version for Multi-Version Coexistence " written earlier is very convenient for testing), and FireFox will not crash either.
After repeated testing, the problem was located: suspended
in the state AudioContext
, when audioWorklet.addModule
+ 构造AudioWorkletNode
was not completed, the call was made at the same time , and the browser crashed at the moment when it was resume
restored to the state. running
In fact, the root cause is that the page is created without user interaction, and AudioContext
the state at this time is likely to be suspended
(the purpose is that the browser prohibits bypassing automatic sound playback without user operation).
I have integrated these test codes into a test file, click here to test , and it is very easy to reproduce in Chrome.
pit filling
Once you know the problem, the solution is simple:
- Method 1: wait until there is a user operation before
AudioContext
creating, and at this time it can be guaranteed that it must be inrunning
the state; - Method 2: Call the method directly
AudioContext
,resume
andrunning
there will be no crash after waiting.
Since this is an open source library, I cannot decide whether the developer will wait for the user to operate, so the second method is based on universal applicability.
After calling AudioContext.resume
, what it returns is an initialization performed Promise
in finally
the block (regardless reject
, the small probability of crash in the small probability can be ignored) AudioWorklet
, that is, to put the original initialization code in one layer.
In addition, under AudioContext.audioWorklet.addModule
the local file://
protocol, Chrome does not support loading Blob Url (FireFox does not have this problem), and it is also Worker, which WebWorker
does not have this problem; finally, it is data url
compatible with Chrome:data:text/javascript;base64,......
Final Results
AudioWorklet
The pits have been filled, and the tests that should be tested have been tested, and a new version using recordings has been released with joy . After the release, I fiddled with it on my mobile phone, hey, why did the recording seem to be a few seconds short. . .
Repeated timing tests on the PC and mobile terminals, and finally issued a statement: Due to 375 callbacks per second inside the audioWorklet, there may be performance problems on the mobile terminal, which may cause the callback to be lost and the recording to be shortened. The PC terminal has no impact, and it is not recommended to enable audioWorklet for the time being.
Therefore, another version was updated, and it was simply restored. The library ScriptProcessor
is still the main force by default, and it can Recorder.ConnectEnableWorklet=true
be used forcibly through the settings AudioWorklet
.
Facing the future, if any browser is officially removed in the future ScriptProcessor
, Recorder will be automatically enabled AudioWorklet
, so the code written now will have great significance for the future, although it is a bit tasteless at present (I feel that AudioWorklet
the support is still written early, and it is a bit vain feeling), but the significance is still great.
For the complete AudioWorklet
implementation code, please move to read: line L157-L281 of recorder-core.js .
【End】