-
Notifications
You must be signed in to change notification settings - Fork 14
Home
If you analysed how the HTML5 player works, you may have noticed that all it played tracks files are available in the network tab of your browser debugger.
- The track URL is generated using the
DZR_AES
key and the trackMD5_SUM
- The track
MD5_SUM
is given only if your request have aDZR_SID
- The track is encrypted using the
DZR_CBC
key
In order to get those keys we must extract them from the player sources. You can look at the sources of the player webworker using the "Sources" tab:
Note that the first line of this worker code is a symbol table, and a few lines later we got the symbol resolver function, which is called each time the script need to call a names function.
In the following sections we will use this translation function a lot.
With this ID, dzr
can now get the full track MD5, otherwise it could only get 30 seconds.
Your Session ID is very easy to find. Just look at the network request panel
of your debugger and you shall see a Set-Cookie line with sid=yoursidnumber
aka the 'Jo' Key for URL Generation
Since the track URL was not part of any JSON we can assume that it was generated by the JS. By looking at the symbol table, we see that we have an 'encrypt' function. Let's have a conditional breakpoint on the resolver when it resolve 'encrypt'. After pressing play on the HTML5 player, out "encrypt" breakpoint is triggered. Now let's take a look at the function scope values we have the following params:
- cdn
- format
- id
- md5
That's all the ingredients required to generate the CDN URL. A closer look to the AES cyphering scope will give us the 16 Bytes AES key.
Congratulation, you just found the AES key, aka the "jo" key, just convert it in ASCII.
[106,111,54,...].map(e=>String.fromCharCode(e)).join('')
aka the 'Gael' Key for Track deciphering
First, add a logpoint on the translator and play a track for 30 seconds.
This will give you an overview of the function in charge of the deciphering.
You can then, traceback those name (for example decipher
)
to they function and have a look at they closure.
The keys are unziped into 2 UInt8Array, in little endian. Zip them back to get the Blowfish/CBC key, aka the "Gaël" key:
[103,52,101,...].map(e=>String.fromCharCode(e)).join('')