1 00:00:00,110 --> 00:00:04,190 MODERATOR: Right now we have a first time DEF CON speaker, Franz Payer, speaking to 2 00:00:04,190 --> 00:00:08,740 you about Exploiting Music Streaming with JavaScript. It's his first time at DEF CON. 3 00:00:08,740 --> 00:00:10,059 Please give him a big round of applause. (Cheers and applause.) 4 00:00:10,059 --> 00:00:13,519 No shots? FRANZ PAYER: Eighteen. 5 00:00:13,519 --> 00:00:15,599 He's 18! (Laughter.) 6 00:00:15,599 --> 00:00:22,599 MODERATOR: I did the same thing. Oh, we're going to give you shots! 7 00:00:24,600 --> 00:00:31,600 He's like no! FRANZ PAYER: All right. I hope you guys 8 00:00:31,810 --> 00:00:37,680 are all awake. So I'm Franz Payer, programmer at Tactical Network Solutions. I'm going to 9 00:00:37,680 --> 00:00:42,730 go over exploiting music streaming with JavaScript. So a couple of acknowledgements before I start. 10 00:00:42,730 --> 00:00:47,090 I would like to thank Zachary Collup and Craig Hefner for all their help and support, and 11 00:00:47,090 --> 00:00:49,870 my employer, Tactical Network Solutions, for letting me to learn about security without 12 00:00:49,870 --> 00:00:55,329 going to jail, which is great. A special thanks to Ronald Jenkies, who is 13 00:00:55,329 --> 00:00:59,329 an independent artist who has given me permission to use his music in this presentation so I 14 00:00:59,329 --> 00:01:05,510 don't get sued by the RIAA. Speaking of which, I want like to thank the EFF for helping me 15 00:01:05,510 --> 00:01:10,350 address issues with the DMCA and the CFAA. However, the decision was made to not release 16 00:01:10,350 --> 00:01:14,540 the original tool which I had planned to. That was a Google Chrome extension that would 17 00:01:14,540 --> 00:01:18,420 showcase all the different exploits and vulnerabilities which I'm going to cover today. But I will 18 00:01:18,420 --> 00:01:20,299 be releasing an alternative tool, which I'll get into later. 19 00:01:20,299 --> 00:01:25,840 I want to state, the views expressed here are mine, not my employer's. 20 00:01:25,840 --> 00:01:32,330 What am I going to be talking about? I'm going to give you background information, what my 21 00:01:32,330 --> 00:01:38,619 project is and what I've done. You have context of like my approach and how I did it. Then 22 00:01:38,619 --> 00:01:42,970 I'll go over the music streaming basics so you understand how it works and implementation 23 00:01:42,970 --> 00:01:48,340 today and what you are going to be seeing. I'm going over my security investigation process 24 00:01:48,340 --> 00:01:54,500 so kind of taking you from the beginning to the end of research to exploitation. And hopefully 25 00:01:54,500 --> 00:01:58,150 by the end you will have a grasp on how you can do this by yourself. 26 00:01:58,150 --> 00:02:02,939 I'll go over an exploit demo, assuming everything works out all right. If there's any time afterwards 27 00:02:02,939 --> 00:02:09,310 I'll talk about my new alternative extension released soon. I'll take questions at the 28 00:02:09,310 --> 00:02:13,590 end. The end goal. Well, originally I planned to 29 00:02:13,590 --> 00:02:17,230 release the Google Chrome extension which will have the exploits which I'm going to 30 00:02:17,230 --> 00:02:22,400 show you. The way it works, it mimics the music player whenever possible. When I was 31 00:02:22,400 --> 00:02:28,349 smart enough to reverse engineer the code and generate the requests the way they did. 32 00:02:28,349 --> 00:02:33,040 Otherwise I would just log whenever I saw some MP3 flying by and look at the syntax 33 00:02:33,040 --> 00:02:38,370 and match that syntax. Every time something matches that syntax flies by, I can give it 34 00:02:38,370 --> 00:02:42,700 that song. The end result you have something in the bag ground. Every time you listen to 35 00:02:42,700 --> 00:02:49,700 a song you can download it. I'm not going to be releasing that. What am I releasing? 36 00:02:51,260 --> 00:02:56,099 It's an alternative, not exactly the same. Forensics tool, not an exploitation tool. 37 00:02:56,099 --> 00:03:01,030 It duplicates requests that it sees flying by and caches it in the RAM. This is helpful 38 00:03:01,030 --> 00:03:08,030 for hex dump analysis afterwards. If you do malware analysis without putting it on your 39 00:03:08,550 --> 00:03:13,230 hard drive you can do it entirely from your browser now. 40 00:03:13,230 --> 00:03:17,170 And this is also helpful if you want to see exactly what is being loaded into your browser. 41 00:03:17,170 --> 00:03:23,040 So here is the wall of shame, a bunch of services which I found vulnerabilities in. Some of 42 00:03:23,040 --> 00:03:29,099 these have made fixes. Some of them haven't. Most of them haven't. So we have Pandora, 43 00:03:29,099 --> 00:03:36,099 Amine, Sound Cloud, Grooveshark, Django, and Eight Tracks, quite a big list. So what is 44 00:03:41,709 --> 00:03:48,709 streaming? Well, which can peed defines it as a way to present details delivered by provider. 45 00:03:49,110 --> 00:03:53,040 So from a developer's point of view this means that you are going to be receiving data in 46 00:03:53,040 --> 00:03:59,170 a really long stream and as soon as you get the first piece you can start processing it 47 00:03:59,170 --> 00:04:05,230 and displaying it to the viewer. From a tactics point of view that means you get use of data 48 00:04:05,230 --> 00:04:10,280 and at the end you have everything to reconstruct the file, a song or whatever. 49 00:04:10,280 --> 00:04:16,900 It is only a matter of capturing the data pieces. Once you do that, there are two technical 50 00:04:16,900 --> 00:04:23,900 major roadblocks from prevent you from playing it back. You have reassembly of the pieces, 51 00:04:24,119 --> 00:04:28,559 typically if you --> like the way the Internet works, when you send data it is not always 52 00:04:28,559 --> 00:04:33,059 received in the same order in which it was sent. This can be more difficult depending 53 00:04:33,059 --> 00:04:39,719 on the type of protocol they use. If you see encryption, that's probably stopping you. 54 00:04:39,719 --> 00:04:42,789 Usually if you want to break encryption, it's not to get music. It's to get someone's password. 55 00:04:42,789 --> 00:04:49,789 That is your major roadblock. The protocols I have seen, typically when 56 00:04:50,330 --> 00:04:55,839 you have some sort of desktop application like Spotify or Pandora 1, they use a custom 57 00:04:55,839 --> 00:05:02,839 TPC protocol. This makes it incredibly difficult to reassemble. A, it's not documented or B, 58 00:05:03,490 --> 00:05:07,689 it's proprietary and you don't know how it works. This probably will stop you dead in 59 00:05:07,689 --> 00:05:10,999 your tracks. However, I noticed that some services like 60 00:05:10,999 --> 00:05:17,999 last FM use http or https because they don't want to write their own custom protocol. and 61 00:05:20,189 --> 00:05:26,990 this is typically what you see in some browser-based applications. So the regular Pandora app, 62 00:05:26,990 --> 00:05:33,479 Sound Cloud, these guys are going to be using http and https. They don't want to do extra 63 00:05:33,479 --> 00:05:38,569 coding. Browser does it for you; why would you want to do it yourself? If you're an attacker 64 00:05:38,569 --> 00:05:43,899 or hacker or whatever, that means you can use the browser, too. Now you don't have to 65 00:05:43,899 --> 00:05:50,369 worry about assembly and de-encryption. That's why I targeted these. They are extremely easy 66 00:05:50,369 --> 00:05:54,129 to go after. And there are two different types of streaming 67 00:05:54,129 --> 00:06:00,429 which I kind of named myself. There's static streaming where you have one URL per song. 68 00:06:00,429 --> 00:06:05,969 So you will have to usually have the file name, know the directory. This is different 69 00:06:05,969 --> 00:06:09,779 from a dynamic one where you have one page and depending on the parameters you send it 70 00:06:09,779 --> 00:06:16,779 you get back a different file. We have a streamed .PHP page and depending on the key you send 71 00:06:17,149 --> 00:06:22,919 it, you get a different file. It's one to one versus one to many. This is important 72 00:06:22,919 --> 00:06:29,919 to keep track of when you're doing analysis. So there are two major types of music players. 73 00:06:30,139 --> 00:06:36,210 Most common one is Flash. This is a majority of the Web players you'll see. However, they 74 00:06:36,210 --> 00:06:42,119 may still use JavaScript. I have seen a lot of people be really lazy and use JavaScript 75 00:06:42,119 --> 00:06:46,860 to pull back the data and then just pass it on to the Flash. All the Flash does is play 76 00:06:46,860 --> 00:06:52,770 it back. Typically because you have Flash libraries made to play back music but not 77 00:06:52,770 --> 00:06:57,300 necessarily customized to work with the interface. This is how they get around it. 78 00:06:57,300 --> 00:07:02,969 However, some services you have to decompile them. I don't know any Flash myself. I skipped 79 00:07:02,969 --> 00:07:07,439 anything that did this. But it's important to know if you are successful 80 00:07:07,439 --> 00:07:13,229 at decompiling the Flash and want to exploit it using the extension in JavaScript, there 81 00:07:13,229 --> 00:07:18,529 are security issues. If there's a key baked into the Flash, you are not going to get it 82 00:07:18,529 --> 00:07:25,249 from JavaScript. The other one you see is HTML5, which is experimental right now. Not 83 00:07:25,249 --> 00:07:29,689 all the browsers have full support for it. You see this in mobile based applications 84 00:07:29,689 --> 00:07:36,689 because Flash is losing support there. This is entirely in JavaScript. So no decompiling 85 00:07:37,229 --> 00:07:44,229 or anything. It's minified most of the time. It's obfuscated and hard to read. 86 00:07:44,959 --> 00:07:50,539 So where is the vulnerability? I went over how the browser does the major work for you. 87 00:07:50,539 --> 00:07:54,569 So what do you have to do? Well, there are two ways of going about this. I mentioned 88 00:07:54,569 --> 00:07:59,800 this earlier. You can copy the requests by kind of just telling based on the syntax of 89 00:07:59,800 --> 00:08:06,089 the URL and this is typically pretty easy. You look at one URL. There's a file name there. 90 00:08:06,089 --> 00:08:10,360 This is the structure. You know, you can easily write an expression to do this. 91 00:08:10,360 --> 00:08:15,059 However, this can be suspicious if they are doing service side logging and they see two 92 00:08:15,059 --> 00:08:20,169 identical requests coming in within million any seconds of each other. They are saying 93 00:08:20,169 --> 00:08:24,779 this is not normal activity. Why is this happening? I haven't seen it being an issue are in terms 94 00:08:24,779 --> 00:08:31,770 of any red flags being thrown up. But this can be limiting. I found services 95 00:08:31,770 --> 00:08:37,190 where they have one-time use tokens. You use a token to stream your music and after it 96 00:08:37,190 --> 00:08:41,779 has been used it is no longer valid. By the time the second request gets there, it is 97 00:08:41,779 --> 00:08:46,949 not valid and you don't get anything back. And the way you get around this is to generate 98 00:08:46,949 --> 00:08:52,149 the requests yourself. This is going to be a little bit more difficult. Sometimes you 99 00:08:52,149 --> 00:08:56,170 can tell based on the syntax of the URL what variables are needed and how you get them. 100 00:08:56,170 --> 00:09:01,370 Other times you have to reverse engineer the code and figure out what they're doing. But 101 00:09:01,370 --> 00:09:07,540 if you are successful you get past the limitation there and it's undetectable when there's sessions. 102 00:09:07,540 --> 00:09:13,550 So if they have sessions, it looks from the service side that two requests are coming 103 00:09:13,550 --> 00:09:16,930 in from two different people in the same IP address and they happen to be listening to 104 00:09:16,930 --> 00:09:23,930 the same song. So how do you go about doing this? Well, it 105 00:09:24,019 --> 00:09:30,490 is important to keep in mind that you have to do breadth before depth. You don't want 106 00:09:30,490 --> 00:09:36,629 to dig yourself in, the first thing you see, waste two hours and find out it's the wrong 107 00:09:36,629 --> 00:09:43,629 thing. Keep track of all your possible options and then take the path of least resistance. 108 00:09:43,649 --> 00:09:49,500 And you want to remember breadth before --> oh, I did that, okay. 109 00:09:49,500 --> 00:09:54,129 Once you keep that in mind, you want to locate the music file in the network traffic. So 110 00:09:54,129 --> 00:09:58,180 you can do this in Chrome by opening up the developer console and then going to the network 111 00:09:58,180 --> 00:10:03,339 tab and you can see all the traffic flying by and there's going to be a lot of traffic. 112 00:10:03,339 --> 00:10:08,579 You want to filter based on exit traffic and sorting possibly by type. The reason you want 113 00:10:08,579 --> 00:10:15,259 to do this, typically when music is loaded in a streaming service, especially Internet 114 00:10:15,259 --> 00:10:21,899 radio service, the music isn't loaded when the page is sent to you originally. Like with 115 00:10:21,899 --> 00:10:25,439 Pandora, the songs are actually loaded after the page has been loaded. This is because 116 00:10:25,439 --> 00:10:31,120 they want to have time to look at your recommendations and figure out what song to give you next. 117 00:10:31,120 --> 00:10:34,079 Also they don't know how many songs they are going to be listening to before but go away. 118 00:10:34,079 --> 00:10:39,790 They have to load this before the fact. This is done through Ajax, which is showing up 119 00:10:39,790 --> 00:10:44,860 as SHR traffic. You sort by type, audio files, because that's probably what you are going 120 00:10:44,860 --> 00:10:49,529 to be finding. Once you find the actual request you want 121 00:10:49,529 --> 00:10:55,529 to inspect any parameters in that request. Headers, any kind of parameters that they 122 00:10:55,529 --> 00:11:00,019 send in the URL, stuff like that. Then you want to find out where those values 123 00:11:00,019 --> 00:11:05,339 come from. And there are many different locations where these values are going to come from. 124 00:11:05,339 --> 00:11:09,720 The first place, you want to do the easiest to the hardest. The first place that is easiest 125 00:11:09,720 --> 00:11:15,660 is the page URL. Sometimes the song ID is in the URL of the page you're on. And you 126 00:11:15,660 --> 00:11:22,029 can use that to get the song. After that you might want to look at the page source, do 127 00:11:22,029 --> 00:11:26,730 a CTRL-F, look for the name of the parameter. You might be able to find it. Then you might 128 00:11:26,730 --> 00:11:32,589 want to look at local storage and possibly cookies. With things like Grooveshark, if 129 00:11:32,589 --> 00:11:36,360 you have a playlist they will send it all to you at once so you don't have to keep making 130 00:11:36,360 --> 00:11:42,589 requests to find out what the next song is. At the end you want to look at JavaScript. 131 00:11:42,589 --> 00:11:48,500 That's hard to read and you have to figure out what someone else's code is doing and 132 00:11:48,500 --> 00:11:52,920 understand when you have everything, you can attempt to replicate the request. Based on 133 00:11:52,920 --> 00:11:57,870 the syntax of the request you've seen as your example, take the parameters you have and 134 00:11:57,870 --> 00:12:04,550 generate the same thing. First target is Amine, a great first target, 135 00:12:04,550 --> 00:12:10,180 they are a Flash based service but use JavaScript to load. And they have almost no security. 136 00:12:10,180 --> 00:12:14,569 I was able to exploit these guys without looking at any code. 137 00:12:14,569 --> 00:12:21,569 So this is the page with the network traffic. I circled the network tab. And at the bottom 138 00:12:22,089 --> 00:12:27,639 you can see that we have an audio/MP3 file which is actually what we're looking for. 139 00:12:27,639 --> 00:12:32,180 So if you want to take the easy way out, you can actually right click this and open it 140 00:12:32,180 --> 00:12:37,920 in your tab and then download it that way. So this is the cheap way out. 141 00:12:37,920 --> 00:12:41,360 (Chuckles.) FRANZ PAYER: Okay. However, I was trying 142 00:12:41,360 --> 00:12:46,019 to show you guys how to automate this with JavaScript. We are going to do more inspection. 143 00:12:46,019 --> 00:12:50,649 Looking at the actual request we see there's actually only one parameter and I took out 144 00:12:50,649 --> 00:12:55,360 all the headers. Those are the standard headers that the browser sends. We had this FID. I'm 145 00:12:55,360 --> 00:13:02,360 going on a hunch and say that FID is file ID. They typically name things like this. 146 00:13:02,999 --> 00:13:09,899 Now you look for the FID. The first place to look is going to be in the URL. Sure enough, 147 00:13:09,899 --> 00:13:14,999 it's in the URL. Great! We have everything we needed. Now how 148 00:13:14,999 --> 00:13:19,939 do I duplicate what they did? So you go and look back at the original request. You can 149 00:13:19,939 --> 00:13:26,230 see that they actually have this weird subdomain thing going on. And I found out with deduction 150 00:13:26,230 --> 00:13:30,829 that the first four characters of the FID are the first four characters of that subdomain 151 00:13:30,829 --> 00:13:35,240 in reverse order. So it wasn't very difficult to figure that 152 00:13:35,240 --> 00:13:39,720 one out. You can easily replicate this using JavaScript, but I'm not allowed to show you 153 00:13:39,720 --> 00:13:45,930 guys exploit code. Next target is Grooveshark. This is quite 154 00:13:45,930 --> 00:13:52,019 a step up. I chose these guys because they have HTML5 and I'm wondering how that would 155 00:13:52,019 --> 00:13:57,600 play out in terms of difficulty. They use several factors of authentication and JavaScript 156 00:13:57,600 --> 00:14:04,600 is minified. It is not for the faint of heart. You want to make sure that you keep track 157 00:14:04,769 --> 00:14:09,720 of what you're doing the whole time. Know what parameters you have, what you are looking 158 00:14:09,720 --> 00:14:14,490 for, what the next target is. Every time you do something new, update your progress so 159 00:14:14,490 --> 00:14:21,490 you don't get lost. It can get confusing. So I went ahead and I want to tell you guys 160 00:14:22,059 --> 00:14:25,689 that you want to have a JavaScript beautifier. It makes it look like the glob on the left 161 00:14:25,689 --> 00:14:32,689 looks like the glob on the right. While you have underscore P, you can have proper spacing 162 00:14:33,170 --> 00:14:40,170 and you can read functions. That's great. Here this is --> I skipped the network analysis 163 00:14:41,499 --> 00:14:46,860 and this is the actual request itself. And I've highlighted that they have --> that's 164 00:14:46,860 --> 00:14:51,430 the URL they have there. All they have is stream key as what you send to them. Off the 165 00:14:51,430 --> 00:14:55,550 bat you think, hey, this is easy. I have one parameter which is stream key. That's what 166 00:14:55,550 --> 00:15:01,819 I'm going to look for. So you also, I looked at all the traffic to 167 00:15:01,819 --> 00:15:08,819 see what was coming. I found this more in the .PHP stream and there's an IDEX method 168 00:15:09,189 --> 00:15:14,389 that takes several parameters. What this will do is return the stream key which is what 169 00:15:14,389 --> 00:15:21,389 we are looking for. So we need the session, the token, the UUID and the song ID. The method 170 00:15:21,559 --> 00:15:25,740 I highlighted. That changes all the time, but we know what it is because it says up 171 00:15:25,740 --> 00:15:31,100 there. So we only need four parameters. I say only 172 00:15:31,100 --> 00:15:37,199 because it actually is easier than it seems. And while I was looking at more .PHP I found 173 00:15:37,199 --> 00:15:42,920 the get communication method which uses a secret key. And I like secrets so I'm going 174 00:15:42,920 --> 00:15:49,600 to keep this in mind. What do we need? From the beginning we know 175 00:15:49,600 --> 00:15:56,600 as soon as we get the stream key we can get the song. To get the stream key we call up 176 00:15:56,889 --> 00:16:03,269 the point --> we need the four parameters and more PHP has the secret key so I'm interested. 177 00:16:03,269 --> 00:16:08,350 I already looked through everything. It's time for JavaScript. 178 00:16:08,350 --> 00:16:15,350 And this is what I get. And in the very first line you see this window.GS.GPL. I'm guessing 179 00:16:16,199 --> 00:16:23,199 GS stands for Grooveshark. Cool, they're storing stuff in the JavaScript environment. Let's 180 00:16:23,290 --> 00:16:30,290 see what they have. I have this window.GSconfig, which has the GS ID. One down. What else is 181 00:16:31,149 --> 00:16:38,149 there? Window.Q.models, which turned out to be the entire playlist you have saved in memory. 182 00:16:39,939 --> 00:16:46,480 Every single song in this playlist has an ID which is the song ID. Right off the bat 183 00:16:46,480 --> 00:16:50,990 we are able to find two of the parameters we needed by looking at the first line of 184 00:16:50,990 --> 00:16:57,519 the JavaScript file. Not bad, but we still need the rest of the parameters. 185 00:16:57,519 --> 00:17:03,529 So I do --> so this is kind of keeping track of everything. We need the token in the UUID 186 00:17:03,529 --> 00:17:10,529 now. I search for that because it was easier. Sure enough I find a function that takes no 187 00:17:10,669 --> 00:17:15,149 parameters, which is good news. Now I don't have to find any more parameters. I can copy 188 00:17:15,149 --> 00:17:21,569 this function and every time I need a new UUID, I call this function. This is an easy 189 00:17:21,569 --> 00:17:27,819 copy and paste. Now we are left with token. This is where it gets more challenging. I 190 00:17:27,819 --> 00:17:34,819 do a CTRL-F for token and I find this F.header.token which turns out to be the token being put 191 00:17:36,990 --> 00:17:42,630 into the header of the request we saw. And so looking at it, it takes, there's a 192 00:17:42,630 --> 00:17:48,270 bunch of stuff that we need. So going top down like you should read code there's this 193 00:17:48,270 --> 00:17:55,010 R.randomizer, remember what I said about function that take no parameters. Copy and paste them. 194 00:17:55,010 --> 00:17:59,960 Sure enough, that's the function right there. That's taken care of. 195 00:17:59,960 --> 00:18:06,960 We need this R.revtoken. I do a CTRL-F for rev token and I find rev token is equal to 196 00:18:07,750 --> 00:18:14,500 N, which is equal to GUI Flubber, which they hoped no one would find. Unfortunately they 197 00:18:14,500 --> 00:18:21,500 shouldn't have put it right on top. So now we really need the current token. Method 198 00:18:24,460 --> 00:18:29,600 was just the method we were calling the URL and we have that documented. So now we just 199 00:18:29,600 --> 00:18:33,440 need the current token. I search for any instances of token because I couldn't find any instances 200 00:18:33,440 --> 00:18:40,440 of current token and yeah, this is where the secret key comes in because get communication 201 00:18:40,559 --> 00:18:45,250 token returns the token that we need for this request and so now we are on a hunt for the 202 00:18:45,250 --> 00:18:52,250 secret key which CTRL-F shows that it is the hex MD5 of the session ID which we found on 203 00:18:53,779 --> 00:18:58,380 the very first step. So we already have everything that we need. 204 00:18:58,380 --> 00:19:04,440 And to just recap, we needed the stream key and we got that by finding these four variables 205 00:19:04,440 --> 00:19:10,320 which were just in the JavaScript and the secret key was needed to get the token. We 206 00:19:10,320 --> 00:19:14,870 have everything and with this information you can generate the request. 207 00:19:14,870 --> 00:19:20,840 But I can't show you an exploit code. So we are just going straight to a demo. 208 00:19:20,840 --> 00:19:27,840 All right. So this is Django.com. Wait, I have to switch. 209 00:19:30,630 --> 00:19:37,580 All right. So this is Django.com, a small music streaming service. It's like an Internet 210 00:19:37,580 --> 00:19:43,460 radio station. The first thing I'm going to do is open up the developer tools and go to 211 00:19:43,460 --> 00:19:48,490 the network tab. And you want to do this before you actually play the song. If you do it after 212 00:19:48,490 --> 00:19:51,730 you play the song you're not going to see it in network traffic because it's already 213 00:19:51,730 --> 00:19:58,730 loaded. Important to keep that in mind. All right. So ... 214 00:20:02,390 --> 00:20:06,909 (Music playing.) FRANZ PAYER: So it plays, which is good. 215 00:20:06,909 --> 00:20:13,909 I'm going to filter based on XHR traffic down here and at the very bottom we have this audio/MPG 216 00:20:15,380 --> 00:20:21,010 file which is what we are looking for. I'm going to click on it and look for anything 217 00:20:21,010 --> 00:20:26,130 that we might need. And it turns out that this is a statically 218 00:20:26,130 --> 00:20:31,710 assigned, static streaming website. So we just need this file name. And it's important 219 00:20:31,710 --> 00:20:36,760 to keep in mind here we have this weird directory thing going on, which is also the first six 220 00:20:36,760 --> 00:20:43,760 characters of the song ID. So if we need it, we have it right there. And because I don't 221 00:20:45,519 --> 00:20:49,220 really know where to look for this file ID because it doesn't have a specific parameter 222 00:20:49,220 --> 00:20:54,470 name in front of it. I can't do a CTRL-F. I'm going to look at the other traffic we 223 00:20:54,470 --> 00:20:59,029 filter on. There's only four other requests, so it's not going to take us very long. 224 00:20:59,029 --> 00:21:05,450 You can see here that this responds with a bunch of JavaScript files. And JavaScript, 225 00:21:05,450 --> 00:21:12,450 it has a like, it has song ID here. But it doesn't actually correspond to the 08061 that 226 00:21:14,669 --> 00:21:20,330 we have. That's dead end right there. But if you look here, this page actually returns 227 00:21:20,330 --> 00:21:26,730 the URL without the file name. Just the whole URL. So this is our target. And if you look 228 00:21:26,730 --> 00:21:33,620 at the headers, they take quite a few parameters. So we have first time, which is equal to one. 229 00:21:33,620 --> 00:21:38,519 I'm guessing that means true. So that's going to be a binary flag. You can probably lie 230 00:21:38,519 --> 00:21:43,880 on that if you want to. SID, which I'm not sure what it is, version number which is probably 231 00:21:43,880 --> 00:21:49,669 going to be the same every time. SUW, which I'm not sure what that is either and CB which 232 00:21:49,669 --> 00:21:53,529 I'm also not sure about. At least now we know what names we are looking 233 00:21:53,529 --> 00:22:00,029 for. At this point I actually notice that I'm glad that Chrome has this, but they have 234 00:22:00,029 --> 00:22:07,029 an initiator column which tells you exactly what script and what line made this request. 235 00:22:07,840 --> 00:22:13,470 So if we click on this, it will actually take us to this line, which if you notice, this 236 00:22:13,470 --> 00:22:19,990 is minified JavaScript. You won't read this easily. I've went and gone ahead and unbeautified 237 00:22:19,990 --> 00:22:26,990 it. We can actually inspect the code. So now if you recall, the URL back here was streams 238 00:22:32,809 --> 00:22:39,809 URL. So we are going to look for any instance of streams. 239 00:22:41,880 --> 00:22:47,110 And sure enough, it takes us straight to the line that creates the request. We have this 240 00:22:47,110 --> 00:22:54,110 underscore JM station ID and some parameters which are set right above it. 241 00:22:54,519 --> 00:23:00,809 And so we can see first time, set it to 1. We have SID which is apparently the session 242 00:23:00,809 --> 00:23:05,240 ID. We have the version number here. And SUW apparently stands for whether the sign up 243 00:23:05,240 --> 00:23:12,240 window is visible or not. So we have everything. Then CB here is apparently 244 00:23:12,480 --> 00:23:17,470 the date and time. So we have everything we need. And I've already 245 00:23:17,470 --> 00:23:24,470 went ahead and wrote a one-line JavaScript which will generate this for us. 246 00:23:26,240 --> 00:23:32,740 So ... this spits out the URL that was generating those new song locations. So I'm going to 247 00:23:32,740 --> 00:23:37,130 copy that. It turns out they actually patched their service three days before I went to 248 00:23:37,130 --> 00:23:42,330 DEF CON and this is freaking me out. Apparently they are doing some weird thing with checking 249 00:23:42,330 --> 00:23:49,159 your session. But I found out to get around it, you can just refresh the radio station 250 00:23:49,159 --> 00:23:55,490 and then it will work. So here we have the next song that would be 251 00:23:55,490 --> 00:23:59,519 playing. If we actually just keep refreshing this, it will give us a different song every 252 00:23:59,519 --> 00:24:00,380 time. (Chuckles.) 253 00:24:00,380 --> 00:24:07,380 FRANZ PAYER: So we can actually get every single song in their music library. 254 00:24:07,380 --> 00:24:14,380 (Applause.) FRANZ PAYER: But I did want to show you 255 00:24:15,909 --> 00:24:20,460 guys an exploit through my Chrome extension. So although I won't be releasing it, I can 256 00:24:20,460 --> 00:24:27,460 show you guys what it looks like. (Music playing.) 257 00:24:29,470 --> 00:24:36,470 FRANZ PAYER: As you saw, there's a pop-up. I clicked on it and it takes us to my Chrome 258 00:24:38,510 --> 00:24:43,769 extension and you can select it and hit download. It's right there. 259 00:24:43,769 --> 00:24:50,769 (Chuckles.) FRANZ PAYER: So not very difficult. So 260 00:24:51,679 --> 00:24:55,899 that was the Chrome extension. I did say that I was going to be releasing an alternative 261 00:24:55,899 --> 00:25:02,899 tool. What is this tool? Well, I'm tentatively calling it Browser Shark until I get sued. 262 00:25:04,210 --> 00:25:10,260 I already bought the domain name, so I'm good. Basically what it is going to do, if you recall 263 00:25:10,260 --> 00:25:14,630 earlier I mentioned I had a method where I would copy any URL that matched the syntax 264 00:25:14,630 --> 00:25:20,710 of the song and then go retrieve it myself. I decided wouldn't it be cool if I could record 265 00:25:20,710 --> 00:25:27,669 all my traffic going through and cache that to the browser and what happens is now I can 266 00:25:27,669 --> 00:25:34,669 -- I can just go to Google and all my traffic will show up right here. What you can do with 267 00:25:34,950 --> 00:25:41,200 this is, you can actually analyze the hex of the request to make sure that you are not 268 00:25:41,200 --> 00:25:45,419 getting any malware. It's nice enough to tell you what type of file it is. If they are lying 269 00:25:45,419 --> 00:25:49,789 to you, you can tell. Like I said before, this would be really cool 270 00:25:49,789 --> 00:25:56,330 with forensics and stuff like that and I'm planning on doing more of coding so you can 271 00:25:56,330 --> 00:26:00,889 do a little bit who are with the hex editor. So this is a tool that I'm going to be releasing. 272 00:26:00,889 --> 00:26:06,820 I will have a location to download it at the end of my Power Point. 273 00:26:06,820 --> 00:26:13,820 All right. Things I learned. Downloading music is inconvenient. 274 00:26:18,529 --> 00:26:22,970 I found that after I had music, I didn't know what to do with it because managing all this 275 00:26:22,970 --> 00:26:28,419 music was a pain. So actually now I honestly just use Spotify. I don't like having to deal 276 00:26:28,419 --> 00:26:29,919 with files. (Chuckles.) 277 00:26:29,919 --> 00:26:34,750 FRANZ PAYER: But services were fairly easy to exploit. I think with all the different 278 00:26:34,750 --> 00:26:40,779 services which I listed at the very beginning, I found exploits in them in three days total 279 00:26:40,779 --> 00:26:46,720 for all of them. The hardest one was Grooveshark which took me a whole day. Pandora was surprisingly 280 00:26:46,720 --> 00:26:50,399 easy. It was impossible, it's actually impossible 281 00:26:50,399 --> 00:26:57,169 to completely protect streaming. Inherently at some point you are going to have your music 282 00:26:57,169 --> 00:27:01,649 on my computer and I own my computer. Even if you use encryption you have to decrypt 283 00:27:01,649 --> 00:27:05,360 it so you can play it back. At that point you can copy the files. 284 00:27:05,360 --> 00:27:12,360 So inherently you can't protect streaming. And SMP things you should know. People have 285 00:27:12,620 --> 00:27:19,620 bad security. This is a shocker. And some people will patch their code. Others will 286 00:27:19,630 --> 00:27:25,279 not. This is the beast of security. It's just the way it works. 287 00:27:25,279 --> 00:27:28,909 And the same Web traffic logging will work with video streaming services, too. Some of 288 00:27:28,909 --> 00:27:34,690 them, not all of them. People ask if Netflix will work. No, it won't, but if you go to 289 00:27:34,690 --> 00:27:40,090 a sketchy Chinese streaming network sites I'm sure this will work as well. But that's 290 00:27:40,090 --> 00:27:45,960 a topic for another day. So I did a case study. Originally the very 291 00:27:45,960 --> 00:27:50,450 first target I found was last F.M. which if you're not familiar with it, it's a British 292 00:27:50,450 --> 00:27:57,159 streaming music service. I found the vulnerability and e-mailed them. I got no response. I made 293 00:27:57,159 --> 00:28:00,470 the Chrome extension, I got no response, but apparently they were able to fix it without 294 00:28:00,470 --> 00:28:06,350 my help. Good on them. These are things I noticed after I fixed it. They secured it 295 00:28:06,350 --> 00:28:11,710 heavily. They capped the bandwidth to match the play back speed. It's impossible if you 296 00:28:11,710 --> 00:28:16,769 wanted to download the whole music library, it's impossible. You have to wait as long 297 00:28:16,769 --> 00:28:22,049 as it would take to play back all that music, which is years. 298 00:28:22,049 --> 00:28:25,740 So that's a good way to prevent people from stealing all your music. They have one-time 299 00:28:25,740 --> 00:28:29,500 use tokens. Like I said earlier, once your first request is made, the second request 300 00:28:29,500 --> 00:28:36,500 is no longer valid so you can't get the music. I tried to do a weird sketchy thing where 301 00:28:37,539 --> 00:28:43,279 I made sure my requests would get there almost at the exact same time. What would happen, 302 00:28:43,279 --> 00:28:48,620 I would get a good ten seconds on my fake stream but it would cut out. They only allow 303 00:28:48,620 --> 00:28:54,130 one stream open at a time. So that was pretty good. 304 00:28:54,130 --> 00:28:57,549 And I couldn't exploit this. And if you wanted to, it would take a huge amount of time and 305 00:28:57,549 --> 00:29:02,519 wouldn't really be worth it, they have obfuscated code and the bandwidth cap makes it so you 306 00:29:02,519 --> 00:29:09,519 can't feasibly take all the music. Mitigations. Using current technology, the 307 00:29:09,659 --> 00:29:13,960 one-time use tokens is definitely the best way to prevent people, like I showed you before, 308 00:29:13,960 --> 00:29:19,539 right clicking and opening a new tab and saving it. The second request won't work. 309 00:29:19,539 --> 00:29:26,539 I've also seen people use RTMPE streams. This is Adobe protocol which they use. E stands 310 00:29:26,919 --> 00:29:31,330 for encrypted. I want everyone to know, because your protocol has an E in it doesn't mean 311 00:29:31,330 --> 00:29:38,330 it's encrypted. I've seen services using non-encrypted traffic and put the E as a protocol. That 312 00:29:39,399 --> 00:29:41,730 doesn't make it secure. (Laughter.) 313 00:29:41,730 --> 00:29:48,669 FRANZ PAYER: And also returning the song in pieces really helps as well. Although so 314 00:29:48,669 --> 00:29:53,490 sound coat actually did this a couple days before DEF CON, but they named all the pieces 315 00:29:53,490 --> 00:29:59,169 in numerical order. That doesn't make it any more difficult for me to put them back together. 316 00:29:59,169 --> 00:30:03,009 (Chuckles.) FRANZ PAYER: For future proofing, you can 317 00:30:03,009 --> 00:30:07,950 take a look at the HTML5 audio tag with support. The guys from Virginia that Tech wrote a paper 318 00:30:07,950 --> 00:30:14,950 on it. I haven't looked much into it. I know inherently that nothing is going to work. 319 00:30:15,440 --> 00:30:20,419 But if someone is interested, that's there. And so these are the references. I actually 320 00:30:20,419 --> 00:30:27,130 have uploaded the browser Shark thing to the Google play store, whatever. So that's the 321 00:30:27,130 --> 00:30:31,750 long URL. I made a lit leaf. If you trust me enough to click on it, I assure you it's 322 00:30:31,750 --> 00:30:38,019 the same link. I'm putting this project on GitHub because I want it to be open source. 323 00:30:38,019 --> 00:30:42,389 It's up there right now, but I don't trust DEF CON WiFi. 324 00:30:42,389 --> 00:30:49,389 That's my blog. I sometimes put interesting stuff on there, sometimes not. No guarantees. 325 00:30:50,870 --> 00:30:56,380 There is my contact information if you want to talk to me. 326 00:30:56,380 --> 00:30:59,710 And I'll take any questions now if anyone has any. 327 00:30:59,710 --> 00:31:04,850 Yes? AUDIENCE: How do you deal with renaming 328 00:31:04,850 --> 00:31:06,419 all the files? FRANZ PAYER: The question is how I dealt 329 00:31:06,419 --> 00:31:13,210 with renaming. In the flat extension, what I did, I wrote a script which would hook on 330 00:31:13,210 --> 00:31:19,049 to the page and I would use jQuery to take the file name and then the artist from the 331 00:31:19,049 --> 00:31:24,759 page itself because they provide that information so the user knows. I actually spent a good 332 00:31:24,759 --> 00:31:28,779 several hours trying to synchronize all the songs together, but that's how I did it. 333 00:31:28,779 --> 00:31:32,139 Yes? AUDIENCE: Why aren't you releasing your 334 00:31:32,139 --> 00:31:35,129 original file? FRANZ PAYER: Because I don't like losing 335 00:31:35,129 --> 00:31:42,129 my money to lawsuit. I can get sued $20,000 per count of trafficking. They have millions 336 00:31:43,169 --> 00:31:46,870 of songs, which would turn into billions of dollars, which I don't have. Yes? 337 00:31:46,870 --> 00:31:52,929 AUDIENCE: (Speaker away from microphone.) FRANZ PAYER: I tried doing this for Spotify. 338 00:31:52,929 --> 00:31:58,340 A guy in Norway or something did the same thing I was doing but happened to release 339 00:31:58,340 --> 00:32:05,340 the code for it. Once before I gave this talk. So they fixed it. It does not work with Spotify. 340 00:32:09,259 --> 00:32:13,899 Yes? AUDIENCE: Did you find that song you downloaded 341 00:32:13,899 --> 00:32:14,629 had a direct ... (Speaker away from microphone.) FRANZ PAYER: It honestly depends on the 342 00:32:14,629 --> 00:32:21,059 service. I think Pandora did a better job of that. Some of them allow users to upload 343 00:32:21,059 --> 00:32:28,059 their own songs and you'll get really weird cover ads as your cover art. It just depends 344 00:32:28,629 --> 00:32:30,090 on the service. Yes? 345 00:32:30,090 --> 00:32:36,889 AUDIENCE: Are these files water marked? FRANZ PAYER: There is no DRM in any of 346 00:32:36,889 --> 00:32:43,850 these. As you saw, I was playing it back in my music player when I downloaded it. There's 347 00:32:43,850 --> 00:32:50,850 no DRM on any of these songs. Any other questions? All right, cool. 348 00:32:52,559 --> 00:32:53,539 (Applause.) 349 00:32:53,539 --> 00:32:53,789 *****