 This is going to be Electro Vault, poning popular desktop apps while uncovering new attack services on Electron. So, let's put it together. Good afternoon, everyone, and thanks for coming to our talk. Let me ask you this. Have you ever wondered how secure it is to open a message within the desktop app you used to chat with your colleagues at work? Have you ever wondered how secure it is to open a source code, which you just downloaded from the internet within your favorite source code editor? What do this electron-based desktop applications have in common and how fundamentally secure are they? Before a year, we set out to find an exact answer to discover what lurks beneath electron applications and throughout the course of one year of our research, we were able to find flaws in more than a dozen iconic applications used by millions of people and uncovered new attack surface within Electron. Hereby, I welcome everyone today to Electro Vault, where I will take you on a journey to hone popular desktop applications while uncovering new attack surface on Electron. So, for the agenda of our talk, first of all, I will start with what is electron and the basics of electron. Then I will explain different security settings which Electron provides. Then we will hack real world applications starting from the least restrictive to the most restrictive settings. And then I will disclose a novel flaw which we discovered within Electron.js framework and at the end, I will end it with mitigations. So, let's get started. So, who are we? I'm Aditya Purani, aka Napstack. I'm a senior security engineer at a leading automotive company. My main areas of expertise are application security and blockchain. And on the weekend, I play CTFs with Perfect Blue. Joining me today is my colleague Max, aka the Grand Pew. Max is a security researcher at Asset Note and he has expertise in application security and blockchain and Max plays CTFs with Waterpeddler. We have two other research members who were not able to join with us today on the stage, but I would like to introduce them as well. So, we have Mohan, aka Sirius, who is a security auditor at Cure53. And we have William Bowling, aka Vax, who is a senior software developer at Biteable. So, let's get started. So, what is Electron? If you can build a website, then you can build a desktop application. That's the main concept behind Electron. Electron is a popular open-source framework used by multiple iconic applications, such as Microsoft Teams, Discord, Slack, and others. Electron is built on top of Chromium and Node.js, which means that by just using HTML, JavaScript, and CSS, you can ship an entirely cross-platform native desktop application. So, before diving into the bugs, it is really important to understand the architecture of Electron. So, for Electron, there are two types of processes. The first one is the main process and the second one is a renderer process. So, main process is the starting point of all the Electron application. Main process can create multiple renderer process using a class known as browser window. On the other hand, we have renderer process, which is used to render web pages using Chromium. And as Chromium is used, a lot of Chromium-related features are involved as well, such as Chrome multiple process, site isolation, and others. It is important to note that there can be only one main process, but there can be multiple renderer process. The way the main process and renderer process communicates with each other is through IPC or inter-process communication module. As you can see in the diagram on the left side, we have a Node shared library. These are the Node primitives, which are provided to both the main process and the renderer process. And as it is not secure to provide Node primitives to the renderer process, we have something known as browser window web preferences or security settings to limit the exposure of Node primitives. So, let's look how this all will look in a code. So, here we have a main process and first of all, we create a browser window with multiple web preferences, which are security settings with either true or false Boolean value. Then we load a URL, which is Google.com, and then we define an IPC event listener known as OpenURL, which will listen for this OpenURL channel and invoke shell.openExternal with the argument. On the other side for the renderer process, it is divided into two parts. The first one is preload.js and preload scripts contain code that is loaded prior to the web page. So, this script run within the renderer context, but are granted more privileges by having access to electron and Node.js APIs, so it can import a Node.js library here. Context bridge, which you see here, is a way to safely expose an API to the web page, which can be later accessed using window object. So, let's see how the web page would look like. So, here we have a web page for Google.com, which was just loaded by the main earlier, and it's a hello world web page where it uses window.electron.openURL and passes an argument to invoke that channel on the main process. So, as we noticed in the main process, we can set multiple security settings to describe what type of renderer process we want. So, if the security setting is, for example, Node integration is true and sandbox and context isolation is false, then it is the most insecure you can get. In this case, XSS is equal to RC. So, it's not a good idea to use this setting. Electron developers also thought about the same, and they came up with a solution, and the solution was to introduce a new feature known as context isolation. So, as you can see in this diagram, there is a slight change compared to the previous one. Now, we have two different contexts. The first one is the application context, and the second one is an isolated context. So, application context is the space where your web page JavaScript would run, whereas the isolated context is where your preload and Electron's internal JavaScript code would run. So, now we have a good segregation between that layers. So, in this situation, the node primitives are only exposed to the isolated context and are not reachable by the web page. And this is a similar concept used by Chromium Browser as well, where it is known as isolated world, where the extension which you install in your browser, its content script JavaScript runs on a different side compared to the web application JavaScript. So, there is an isolation there. So, throughout our talk, the attack surface would be the renderer process, and we will be start by abusing the least restrictive configuration and then move on to the complex exploits. So, to keep the slides clean, let us keep following terminologies in mind. So, I talked about node integration, context isolation and sandbox, but don't worry right now about node integration in workers and node integration in subframes. I'll talk about it in the coming slides. So, first situation, everything is red. Node integration is true, context isolation is false, and sandbox is false. In this case, it is very easy to get a shell as node is directly exposed to the renderer. So, a web page can just do require child process and exec their own shell command. So, the only thing you need to do as an attacker is to find a way to embed your JavaScript within the web page. So, again, we return to our schematics and the circle which is mentioned in the red is the area which we are targeting at this point. So, let's take a look at a real world case study where we were able to abuse this specific configuration to get RCE. So, we will look at VS code, remote code execution, which bypasses the restricted mode. So, VS code is a very commonly used source code editor. And when you open a project within VS code, it will prompt you that you wanna load this project in a restricted mode or you wanna open it in unsafe mode. So, this particular RC which I'm about to demonstrate will work on a restricted mode of a VS code. So, the bug here is we were able to find an XSS in markdown which was subjected to very strict CSP and electron policy and we were able to chain it with multiple bugs to get an RC on an insecure window. So, let's see how this works. So, this diagram is the entire exploit chain for VS code and here you can see three squares which I marked with different color. So, there is one with green, orange and red. So, the square which is marked in green is running with the most tight electron configuration which is the most secure. And our goal is to somehow go from that green to red. The red one is the one which is running with node integration true, which is the most insecure configuration which I talked about earlier. So, how do we do that? So, if you know on VS code when you open a project and when you load a markdown, it is not rendered by default. So, first of all, you need to create a malicious project and create a folder known as dot VS code. Within this folder, you can create a JSON file which is settings.json and you can enable markdown previewer. So, as soon as this project will load, it will not just put a code block but it will render the markdown. So, once a markdown is rendered, you can put your own JavaScript to get XSS but in the first window, the markdown previewer window, it is subject to a very strict CSP policy where on the script tags, it is subject to nones. So, unless there is a way to leak nones, we cannot embed a script tag. So, what we did here is we perform a meta redirect which is a way to redirect to an external site within the markdown. And once it redirects to our own site, it is not subject to that CSP policy. So, we can run arbitrary JavaScript. We also use an attack known as XSS leak in order to leak the origin of where this XSS execution was happening. And this leak provide us access to extension ID of VS code. So, if you have used VS code, there are multiple extensions you can install. And these extensions come with their own unique identifier which is a GUID string which is not guessable. So, we need to leak it. So, we leak that in the step number one. And step number two, as we land on attacker.com website, we can get an XSS on the second protocol frame which is VS code web view. So, there is an XSS vulnerability within the extension VS code web view protocol frame. And we use this XSS to make another post message to the top layer protocol frame which is VS code file. So, we send a post message known as channel do read. And what this will give us a response is it will give you the user directory where this project is running for. And this is important for the reliability of the exploit because you need to know where the user has downloaded it on their file system to perform further exploitation. So, once you leak this user directory, what you can do is you can perform a redirection to VS code file protocol which works similar to file protocol. Like if you have used file, ETC password to read a file. But the catch here is this protocol can be invoked from any origin, unlike the traditional file protocol. So, what we do is we do an attack which is VS code hyphen file colon slash slash. And then we perform part reversal with dot dot slash and append this directory which we have already leaked earlier in the previous step. And then we render an HTML page which does top dot require child process and get access to the node module because that is the window which is running with node integration through. So, let's see how this exploit would look like in real world. So, the victim has opened VS code here and now they will try to open our markdown. And as you can see, a calc is popped and that is our demo for the VS code, remote code execution. So, we received a bounty for $6,000 from Microsoft for this remote code execution bug. And the main takeaway is that if you are a developer for an electron app, it is important to consider all your windows as a part of the threat model and apply the most restrictive settings on all of them rather than just one of them or two of them. So, let's switch gears a bit and increase the restrictiveness a bit more. So, here we have context isolation is true. And as context isolation is enabled, node is not directly available to the renderer. So, we cannot use an exploit like the previous case where we just require a node library. So, there are two ways to exploit this situation. So, as you noticed here, sandbox is false. So, we can use a Chrome V8 renderer exploit. So, you can go to CR bug, find a crash proof of concept or a full blown Chrome and run it. Or you can find a way to disable context isolation somehow and that I will show you how we did in the coming slides. So, within our diagram, now we have two different separate context. XSS is on the application side and the node and electron API resides on the isolated context. So, there is enough segregation at this point. So, case study two, we will talk about Discord RC. So, Discord was using electron version 12.14.1 which was an older version when we tested on the latest Discord version. But it also means that it is indirectly using an older version of Chrome, which is Chrome 83. We found XSS in one of the video embedded in Discord. So, if you have used Discord when you chat with someone and you send them a YouTube link, it will expand and someone can click on that link and just watch it within Discord, the YouTube video, rather than going to the YouTube website. So, we were looking for embeds to figure out what sort of vulnerable embeds we can find and we were able to get XSS in Vimeo, which is another famous video sharing service. And we exploit this XSS and perform our attack. But the problem here is that iframes or embed in electron are sandboxed by default. So, we cannot just simply run a V8 exploit and perform our exploitation. So, what we did is we dig deeper into the Discord source code and we abused electron misconfiguration to open new window using window.open and this new window was loaded with sandbox disabled. And now we can easily navigate to the attacker site and run our Chrome V8 exploit. So, let's say Discord RCA. So, the malicious actor is gonna send URL to the victim and victim will try to interact with the URL. And as you can see, a new window has opened. This is without sandbox and we have this sandbox payload here, which is gonna pop a calc. So, we were awarded around $5,000 bounty for this bug in Discord. And Discord fixed it by upgrading to the latest electron version and also fixed this new window opener bug. So, next time when it opens a window, it will be open with a sandbox enable. And most of you might be knowing about this issue of running a renderer exploit to exploit electron apps, but what I'm showing you is that it is really common to have this in real world electron applications. So, for our next case, we have node integration to false. Sandbox is true in this case, but this time the context isolation is false. So, as sandbox is true, sandbox is enabled on the renderer process. So, we get the protection of Chrome Sandbox, which uses setcomp on Linux or Win32K lockdown on Windows. So, node or modules are exposing the renderer because node integration is set to false. But now, as context isolation is disabled, there is no isolation between the website you load and electrons internal or preload code. And let's see what I mean by that. So, in the diagram here, previously we had two separate contexts, but now the electrons internal code, preload and application all run within one single context. So, what can we do here? Because electrons internal code is running JavaScript as well. So, can we do something like prototype pollution and overwrite certain JavaScript function? Let's see. So, how to get a shell? So, if electron version less than 10 is used, then you can use a prototype pollution gadget to leak a remote or IPC module. So, according to electron documentation, remote module is used to bridge JavaScript objects from the main process to the renderer process. So, when you leak a remote module, even in a sandbox window, you will get access to node primitives. From electron version 10 to 14, electron developers thought that remote module is a very dangerous feature. So, they switched its default value to false, but developer can still go out of their way and enable it. So, you can do the same. You can use prototype pollution to leak remote or IPC. And most of the time, remote module is disabled because developer do not do that in this common apps. So, you need to find some sort of IPC misconfiguration to leverage it to RCE. Let's look at the third case. So, electron version greater than 14, which are the newly electron versions. In this case, remote is completely deprecated. So, there is no feature called remote, but developers can still do an NPM install electron slash remote to install it, but it is really uncommon to see that. So, what we do here is we leak IPC module, and our goal is to find an IPC misconfiguration within developer-defined IPC channel, like OpenURL, which we saw, or Electron's internal IPC channel. So, this is the novel prototype pollution gadget we discovered for the late-test electron version. And the concept of prototype pollution on context-disabled window was first proposed by Masato Kinugawa in 2018, but that exploit was working on the older electron version, and this one would work even on the late-test one. So, what this exploit does it, I overwrite certain JavaScript inbuilt properties, like Ends, Width, and Call, and on number three, I get access to Wepec Require, which contains all this node electron modules which you can use to pop a calc in your favorite apps. So, for a situation where sandbox is false and context isolation is false, you may be wondering why not just run a V8 exploit, but with prototype pollution, with Wepec Require, you get access to node primitives, and you get access to Electron Common API, which can be easily used to pop a calc. So, the benefit for using a prototype pollution compared to a V8 exploit is that here, you don't require any binary exploitation skill. It is a complete web attack. The second one is it is more reliable compared to, for example, a V8 exploit which can be more of a heap massaging in certain cases. And the third one is what if the app which you are targeting is using a very latest electron version, which doesn't have any Chrome and within the patch gap. So, this will be helpful. But let's return to our original case where sandbox is true. Let's see what we can leak. So, in this case, we don't have access to node or Electron Common APIs like previously, but what we can do is we can leak Electron's internal IPC bindings. For example, IPC renderer and IPC renderer internal. So, the IPC renderer is used to invoke developer defined channels, whereas IPC renderer internal is used to invoke Electron's internally defined channels. So, let's see how we use in a real world app. So, what I'm gonna talk about is a local file read in Microsoft Teams which leads to account takeover. So, Microsoft Team was using an Electron version less than 15. We found an access in renderer using a zero-day in CK editor which is used for rich text formatting for markdown. And what we noticed is when you create a new window similar to Discord, context isolation is disabled and sandbox will be enabled. So, as context isolation is disabled, what we can do is run the prototype pollution gadget, leak the IPC using XSS. So, once we leak this IPC bindings, we were not able to find any misconfiguration within developer defined IPC in Microsoft Teams. But, we were able to notice a misconfiguration in Electron's internal IPC. So, Electron has this IPC channel known as native image create thumbnail from path which takes a path and reads that file and gives you an output. Think of it as a local file inclusion or local file read. So, what we were able to do is, in Microsoft Teams, we were able to read desktop config.json, which contains user-specific property including the JWT token of the user. So, let's see how the expert would look like. So, here, the XSS is triggered. And as you can see on the attacker's website, they have access to desktop config.json. It is a bit small to read, but this is a content of the file which contains the access token of the users. And with that, they can compromise the victim's Microsoft Teams account. So, we received $3,000 bounty from Microsoft for this issue. Let's move on to the last scenario where everything is green. So, this type of app runs with the most secure settings and it is used by most of the application. So, node integration is false so you cannot get node primitives directly on the webpage. IPC cannot be leaked because context isolation is enabled and it is fully sandboxed. So, to hack this is the main part of our research. So, in the diagram, we are right now in the sandbox renderer and this is the most safest configuration possible in Electron today. So, at this point, you might be wondering that in this case, XSS in an Electron app would be same as XSS in a browser and the answer to that is no. The reason is that Electron apps are not same as your day-to-day use Chromium browser. Electron app is a combination of Electron, native C++ code and Chromium code. So, can we somehow find a way to abuse this intersection between Chrome and Electron and subvert all the security features possible? Let's see. So, we move on to enabling node integration in subframes from a compromised renderer which is a CV which was assigned to our findings. So, let's first talk about what is node integration in subframes. So, let's say you have a web page which is called example.com and within this web page, you create multiple iframes to load another web page. Now, let's say if you want to provide this iframe access to node primitives or preload APIs, then how would you do it? The answer to that is enable a feature known as node integration in subframes. So, once you enable this feature, all your child windows or subframes will have access to node primitives or context bridge exposed API. So, for every subframe, if your parent page example.com has node integration enabled and sandbox disabled, then node JS primitives will be available within your iframes. If node integration is disabled and sandbox it doesn't matter, enable or disable, then all your preload or context bridge exposed API will load within the iframe. So, let's take a look in the code to understand it a bit more. So, main process, here we have node integration in subframe set to false. Renderer process we defined open URL channel, just like the first example. And this is our main window which is google.com. What it does it, it creates an iframe with a URL porn.af. And then it access window.electron.openurl. Works fine. But when you try to access window.electron.openurl from the iframe, it's gonna throw an error. Why? Because node integration in subframes is disabled. This case, let's turn it to true and let's see what happens. So, here iframe will have access to that context bridge exposed or preload APIs and is able to invoke it successfully. So, most of the time when we get accesses in all these apps, it is usually in embeds. So, for example, if you saw with this code we had an access in Vimeo embed. And in this case, a node integration in subframes is mostly disabled because developers again, do not go out of their way to enable it. So, it's a bit sad because you don't now have access to context bridge exposed API. So, what can we do here? Can we still hack it? Let's see. So, let's take a deep dive into how node integration in subframes is enabled in Electron. So, Electron patches a blink web reference and adds security featured flags. For example, it implements node integration in subframes by patching this file. And this is the code where that entire logic of enabling and disabling a feature takes place. So, if you are able to read or not, there is a file which is under a directory known as shell slash renderer. It's a renderer folder. And this file contains a code in which the area marked as red has something like renderer frame where it gets access to blink web preferences and then access like a property which is node integration in subframes. And based on the value of it, one or zero, it's gonna enable or disable it. So, if you are paying careful attention, you see that this feature and all these checks were implemented on the renderer side and not on the sandbox side. So, if you can use a renderer Chrome V at exploit and set node integration in subframes to one, then it should be able to enable it. So, let's look at an annotated version of our binary exploit. So, here on number one, we get access to the web preferences offset in the memory. Then we add this static offset to get access to node integration in subframes and then we overwrite its value to one from zero, which means enabling it. Let's see where in real world application we were able to find this. So, Element is one of a commonly used texting app and it was using Chrome 91 and Electron 13.5.1. We find an access on embed through a deep link misconfiguration and as we had access on embed, no context bridge API was exposed to embed. So, we run a Chrome renderer V8 exploit for Chrome 91 to expose context bridge API on embed. So, this is the code of Element. Here, they define a channel on main.js known as user download open and whatever the argument is passed, it goes inside a dangerous node.js function which is shell.openpath. This is a dangerous thing for arbitrary code execution. On the other side on the preload, it exposes a send method to the web page and which you can pass any channel and argument to it. So, as a diagram, let's go from sync to source. So, main.js contains our RC sync. Preload.js contains send method. Your main website of Element has access to window.electron.send, but your XSS doesn't have access to that API. So, with your exploit, what you can do is you can run a multi-stage exploit. For the stage one, you run V8 exploit and send node integration in subframes from zero to one, which enables it. And on the stage two, you create an iframe within your first iframe and this second iframe will load with node integration in subframe true, so it will have access to that send method which you want to get that code execution. So, this is the code version of the exploit and I create an iframe within iframe after enabling node integration in subframe. So, this will create another iframe and that's gonna pop a calc. Let's see how it looks like in the demo. Attacker is sending a URL to the victim. Victim is opening in the browser. They're gonna open in Element app. So, it's a video conference. Everyone wants to join a video conference. So, let's tap on join conference. And as you can see on the console, this is where our exploit is running behind the scene. It takes time to perform this heap massaging and calculating all this offset. And as you can see, we popped a calc. So, we received $3,000 bug bounty from internet bug bounty program and they fixed this entire electron specific feature by not exposing this context bridge IPC to child renderer process. So, if you do the same in the latest electron version, you won't be able to get access to window.electron.send within the iframe inside your iframe. So, second we move on to disabling context isolation, the most coveted feature of Electron.js from a compromise renderer. So, same story, Electron defines that on the renderer side as well. In the code, we again go to shell slash renderer folder which is a renderer side code and it gets context underscore isolation variable in step one from blink web preferences for a renderer frame. And then on the step two, it has a boolean which is should create isolated context which is based on the value from step number one. And at step three, there is a if statement. If it's true, then enable context isolation. If it's false, don't enable. So, same story, use a v8 Chrome renderer exploit and set context underscore isolation from one to zero. So, our annotated exploit would look the same as the previous one. We get access to context isolation in the memory and then we overwrite to zero from one. So, let's take a look at our final case study where we found RC in an undisclosed app. This app was using Chrome 94 and Electron version 15 and it had a feature to embed untrusted content within iframe. So, the code looks like this. On the right, we have the main.js which defines the same open underscore external channel which goes into dangerous node.js sync. On the left, we have a preload.js of which implements a wrapper and has a function known as is allowed URL. This is allowed URL function. We'll check whether a URL starts with a file protocol which is HTTPS. So, if we try to use a similar exploit as previous, it's not gonna work because we were passing like file path to calc.app. And in this case, file is the protocol, not HTTPS. So, let's see what we can do here. So, schematics, again, if we try to run the node integration in subframe exploit, we have access to open external URL API which was defined on the preload but still it will be subjected to the HTTPS check. So, how can we somehow directly make a call to the main process from our iframe? Let's see. So, here is our exploit. On the stage one, we will run a vate exploit to change context isolation from one to zero which means disabling context isolation. Then we perform a redirect after that step has happened and we load a stage two which is another page on your attacker website. And here we perform a prototype pollution attack which I showed you in the earlier slide for CI disabled windows. And this prototype pollution will leak you IPC bindings. And once you have access to this IPC binding, you can make a direct call to the main process using IPC.send with that particular IPC. So, here we are making a direct call to the main.js. So, this is our exploit. This is how it looks in the code. So, this is the disabling part. We redirect to leak.html. We perform our prototype pollution and we do an IPC.send with two arguments within the first is channel and the second is file part to calc. So, let's see how our exploit would look like. So, this is that famous undisclosed app running over exploit. So, as you can see, it is calculating certain offsets and then it is gonna perform the same thing which we had in the previous example. So, this will be its log. And as you can see, now we have access to the click me, which can pop a calc. So, we received $5,000 bounty for this bug for this program. So, now we will take a look into same site origins spoofing. So, for example, this is your shiny new electron app and it is loading a web page known as main.example.com. This web page creates two iframes. The first one is youtube.com and second one is sandbox.example.com. So, let's see how the process are created within electron apps. So, it creates a separate process for youtube.com but it uses the same process for main.example.com for the sandbox.example.com. And this happens because Chrome has a feature known as site isolation and site isolation doesn't apply when your top level domain are the same. So, in this case, the common between the main and sandbox.example.com is the example.com top level domain. So, Chrome uses the same process of both page. So, in this case, if you are exporting a real world app and you have access in sandbox which is on the sandbox.example.com process, then what you can do is, within a Chrome renderer v8 exploit, you can change document.url to main.example.com and security context origin port to 443. This way, you will be effectively able to masquerade to your parent window and are able to access all the context bridge exposed APIs or node primitives which are available to the main window. So, this is one way to do this. So, let's talk about patch gap. So, as we noticed in a lot of this real world applications, we have used Chrome v8 renderer exploit. You might be wondering, is it really very likely to use a v8 exploit in all this real world app? And the answer is yes. And this stems from the fact that there is a noticeable patch gap between Chrome, Electron and Electron applications which makes most of them susceptible to this attack. And an adversary or an attacker can also go one step further and can use sandbox as for Chrome. But here, which I showed even with a renderer exploit, you can do a lot of stuff and just defeat the entire ElectronJ security features. So, let's talk about the mitigations. So, for the developers, I would suggest that enable all the security features because a lot of this bugs which we submitted to ElectronJs frameworks were fixed promptly by it. But there is a design flaw which is present in the ElectronJs framework which allows you to access these features from a renderer process. So, this flaw is currently still present. So, even with a renderer expert today, you can disable context isolation, for example. But ElectronJs developers have took enough step to not expose APIs, for example, in node integration in subframes which prevents a few of our exploits here. So, if you are using an app, make sure to upgrade your Electron version very regularly. So, if you are a developer who is always keeping up with the pace of this Electron releases, then you should be pretty much safe for this patch gap and it would be narrow. And if you have an organization who can maintain your own fork of Electron, you can cherry pick this V8 fixes and can deploy it there to be one step further. So, another important aspect is to don't use a third-party embeds on your website. We saw that the failure point with Discord was to use Vimeo embed, for example, here. So, make sure that you use pretty trusted embeds and even if you use, make sure you have enough defense in depth because that embed can lead to like a code execution in your own app. So, be careful about that. And the last suggestion here is to mitigate vulnerabilities across all your assets. So, even if you have subdomains, as we saw that you can use an access on subdomain and then just go back to the main window using the same site exploit. So, that should be the part of our mitigations. So, as a part of our epilogue, what I wanna mention is we were able to compromise 20 different electron applications. These are used by millions of people. And some of the examples which I didn't show in the talk are JupyterLab, Mattermost, Basecamp, Notion, RocketChat, and others. So, for our takeaways as a part of this talk, I wanna emphasize on three key points. The first one is related to bug bounty hunters and security researcher. And it is to dig deeper into the framework which you are auditing and to not limit yourself to the application layer. So, in our research, we didn't stop on just the JavaScript side of the things on Electron, but we took a look into how these features were implemented and what are the possibilities to tamper with those. So, go as deep as possible when you are auditing these sort of frameworks. The second one is Electron apps are a very ideal adversarial or red team target. As you can see all this app discord element, you just send a link and it just requires single click and some of our exploit even doesn't require a click and you can gain a system level shell on the operating system. So, users are gonna open the link, they are going to join conferences and they are going to click on certain stuff. So, this is really important and if you are on the detection team or blue team, it is important to also consider Electron's app as a part of your threat model and see it as a same entry point as any other asset you have in your organization. The third one, if you are a developer, minimize attack surface on your application as much as possible. So, Electron is not bad. I would say if you are implementing and doing all the base practices, it is still gonna provide you and guarantee you security features, but you need to work towards that. You need to minimize this attack surface. So, a good example to this is a textbook low-level attack known as open URL redirection, which is a PFI on a lot of bounty program. In Electron app, if you find open URL redirection, you can redirect to your own website and you have control to the window and then you can just run this Electron exploit to gain RC. So, who knows, some days open, sometime open URL redirection in your app can lead to RC. So, please pay careful attention to your assets as well. So, at the end of this, I would like to thank everyone for coming and viewing our talk and for your attention, time and interest. And if you wanna understand in details about our findings, we have created a website which is electrovol.io. And within this website, there is a menu for blog which opens blog.electrovol.io and there you can find proof of concept and this exploit code for the use cases which I mentioned here. And we will be also updating this site time to time to include all the 20 use cases and Electron.js specific flaws. So, with that, I conclude my presentation here and thanks again for coming to see ElectroVolt.