├── README.md ├── index.js ├── package.json ├── neeo.xml ├── udp3201.js ├── autoupdateGuiOnXMLChange.js ├── c.cert ├── guidata.xml ├── https.js ├── guidata.1.xml ├── c.key ├── http3000.js ├── gui2.xml └── gui3.xml /README.md: -------------------------------------------------------------------------------- 1 | "# FakeBrainTool" 2 | -------------------------------------------------------------------------------- /index.js: -------------------------------------------------------------------------------- 1 | const http3000 = require("./http3000"); //CP6 emulation 2 | const udp3201 = require("./udp3201"); //Incomming button commands. 3 | const https = require("./https"); //Firmware research. 4 | const autoupdateGuiOnXMLChange = require("./autoupdateGuiOnXMLChange"); // XML file modification check. 5 | -------------------------------------------------------------------------------- /package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "fakebraintool", 3 | "version": "1.0.0", 4 | "description": "Fake bain tool", 5 | "main": "index.js", 6 | "scripts": { 7 | "test": "echo \"Error: no test specified\" && exit 1" 8 | }, 9 | "author": "Niels de Klerk", 10 | "license": "ISC", 11 | "dependencies": { 12 | "dns-js": "^0.2.1" 13 | } 14 | } 15 | -------------------------------------------------------------------------------- /neeo.xml: -------------------------------------------------------------------------------- 1 | 2 | 0.53.8 3 | 4 | /1c5e991f04ecf55708298be91907df8894a0c38c/neeo_release.bin 5 | 6 | 0x1e6eea06 7 | 8 | /1c5e991f04ecf55708298be91907df8894a0c38c/recovery_release.bin 9 | 10 | 0xf78e7c6a 11 | 12 | /1c5e991f04ecf55708298be91907df8894a0c38c/bootloader_release.bin 13 | 14 | 0x4aa8d510 15 | 16 | 17 | -------------------------------------------------------------------------------- /udp3201.js: -------------------------------------------------------------------------------- 1 | const dgram = require("dgram"); 2 | const server = dgram.createSocket("udp4"); 3 | const TCP_PORT = 3201; 4 | 5 | server.on("error", err => { 6 | console.log(`server error:\n${err.stack}`); 7 | server.close(); 8 | }); 9 | 10 | server.on("message", (msg, rinfo) => { 11 | console.log(`Button press: '${msg}'`); 12 | }); 13 | 14 | server.on("listening", () => { 15 | //const address = server.address(); 16 | console.log("N330 UDP service running on: UDP/" + TCP_PORT); 17 | }); 18 | 19 | server.bind(TCP_PORT); 20 | -------------------------------------------------------------------------------- /autoupdateGuiOnXMLChange.js: -------------------------------------------------------------------------------- 1 | const fs = require("fs"); 2 | const interval = 2000; 3 | const GUIXML = "gui2.xml"; 4 | const GUIData = "guidata.xml"; 5 | let guiTime = 0; 6 | let ignoreChange = true; 7 | 8 | function intervalFileCheck() { 9 | let stats = fs.statSync(GUIXML); 10 | if (ignoreChange) { 11 | guiTime = stats.mtimeMs; 12 | ignoreChange = false; 13 | } else if (guiTime != stats.mtimeMs) { 14 | guiTime = stats.mtimeMs; 15 | ignoreChange = true; 16 | let time = Date.now(); 17 | updateGUI(GUIXML, time); 18 | updateGUI(GUIData, time); 19 | console.log(`gui.xml file changed: ${guiTime}`); 20 | } 21 | } 22 | 23 | setInterval(intervalFileCheck, interval); 24 | 25 | function updateGUI(XMLFile, time) { 26 | var fs = require("fs"); 27 | fs.readFile(XMLFile, "utf8", function(err, data) { 28 | if (err) { 29 | return console.log(err); 30 | } 31 | var result = data.replace(/projectId=\"[^\"]*\"/g, `projectId="${time}"`); 32 | 33 | fs.writeFile(XMLFile, result, "utf8", function(err) { 34 | if (err) return console.log(err); 35 | }); 36 | }); 37 | } 38 | -------------------------------------------------------------------------------- /c.cert: -------------------------------------------------------------------------------- 1 | -----BEGIN CERTIFICATE----- 2 | MIIC+TCCAeGgAwIBAgIJAPmcKzKUyrGtMA0GCSqGSIb3DQEBBQUAMBMxETAPBgNV 3 | BAMMCDEwLjIuMi4zMB4XDTE5MDIwNjE2MTYyNFoXDTI5MDIwMzE2MTYyNFowEzER 4 | MA8GA1UEAwwIMTAuMi4yLjMwggEiMA0GCSqGSIb3DQEBAQUAA4IBDwAwggEKAoIB 5 | AQCvkgE+E9HzVM4jFmr8FtBe+ALXQJdWtmuT/d9psPDGlinsV3mmDWfu/WTO8edu 6 | TpbwGSWO7raaQG6MyzDHwU9lzjqlITcLmuyGyz9dwHZmxgiz7xX/dB45Q+yNCIW0 7 | POtojS4Kjr7nQg/P0Z3iQiN8WF/nXZ1fh1nX5qUj2NGcahUpLkem6R3ZwRHKZoGo 8 | fv/TGLK3dkxsLMwqwkuxSAe8T2+j5j8yhWNMN557e5m1ReSLxb96w2W+CWGl84+B 9 | jkwim7oKTK9pI/Td0Z8SIYLERxf6+G2xr+YlrozV7MviBDoz9EZakoeNOx7eLsMs 10 | 7UrJzmYq5w3dUV+CFvKjUeezAgMBAAGjUDBOMB0GA1UdDgQWBBTGTIxyyW6ZEmbF 11 | 5AMVdSbvS6N6iDAfBgNVHSMEGDAWgBTGTIxyyW6ZEmbF5AMVdSbvS6N6iDAMBgNV 12 | HRMEBTADAQH/MA0GCSqGSIb3DQEBBQUAA4IBAQAA8B2xADLuy0A8+9BpZYyaiHAv 13 | LUCtC6TP6U8z4895+vkzEb9eSloyptQv5utbG3O1og16PGg/TvwriMkLVzKYlXqQ 14 | p3zK0k/XGWkWHjMU7NqXYY3eZt9u+Z41j+PjySDg34hoYdro4VBRZ0qwumgpI4+E 15 | 4Nis1kRQ5DHvdNedI9oAkJx+cdYGLBxOa393xfOLBxDMd2YucntZU537KlhvRwHp 16 | gLlT2HFPJfmlcrh1LMyjjWi/rN9I/fnBJ+kK82Q9gj17eGCJslK1H5Vx0TiYoe9W 17 | r5T88CNA6+n54HSjS+G+plrk5Tigy+UhpN9dztNl5uBAwxlbDzywiGRWdczD 18 | -----END CERTIFICATE----- 19 | -------------------------------------------------------------------------------- /guidata.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | Vette muziek title 5 | 6 | Little Dino JaY 7 | 8 | www.google.com/images/branding/googlelogo/2x/googlelogo_color_272x92dp.png 9 | 10 | 11 | v1/imagecache/getlazyresized/lz4-black/480/480/http%3A%2F%2F10.2.1.30%3A1400%2Fgetaa%3Fs%3D1%26u%3Dx-sonos-http%253alibrarytrack%25253ai.8WdG64vCRvYXZ7.mp4%253fsid%253d204%2526flags%253d8224%2526sn%253d1 12 | 13 | 14 | v1/imagecache/getlazyresized/lz4-black/480/480/http%3A%2F%2F10.2.1.30%3A1400%2Fgetaa%3Fs%3D1%26u%3Dx-sonos-http%253alibrarytrack%25253ai.MoxqJEgSkqgZRp.mp4%253fsid%253d204%2526flags%253d8224%2526sn%253d1 15 | 16 | true 17 | 18 | -------------------------------------------------------------------------------- /https.js: -------------------------------------------------------------------------------- 1 | const https = require("https"); 2 | const fs = require("fs"); 3 | const TCP_PORT = 443; 4 | const options = { 5 | key: fs.readFileSync("c.key"), 6 | cert: fs.readFileSync("c.cert") 7 | }; 8 | 9 | let responseData = { 10 | code: 200, 11 | type: { "Content-Type": "text/html; charset=utf-8" }, 12 | content: "" 13 | }; 14 | 15 | const neeoSServer = https.createServer(options, (req, res) => { 16 | const method = req.method; 17 | const uriparts = decodeURI(req.url).split("/"); 18 | const clientIp = req.connection.remoteAddress.replace(/^.*:/, ""); 19 | 20 | console.log("Method: " + method); 21 | console.log("url: " + req.url); 22 | console.log("clientIp: " + clientIp); 23 | if (req.url == "/firmware_info.txt") { 24 | responseData.content = "0.50.6-20180424-481315c-0523-151625"; 25 | responseData.content = "0.27.0"; 26 | } 27 | 28 | res.writeHead(responseData.code); 29 | res.end(responseData.content); 30 | }); 31 | neeoSServer.listen(443, function() { 32 | console.log(" NEEO S Service running on port: " + TCP_PORT); 33 | console.log("-------------------------------------------------"); 34 | }); 35 | -------------------------------------------------------------------------------- /guidata.1.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | Vette muziek title 5 | 6 | Little DinoJaY 7 | 8 | v1/imagecache/getlazyresized/lz4-black/80/80/http%3A%2F%2F10.2.1.30%3A1400%2Fgetaa%3Fs%3D1%26u%3Dx-sonos-http%253alibrarytrack%25253ai.8WdG64vCRvYXZ7.mp4%253fsid%253d204%2526flags%253d8224%2526sn%253d1 9 | 10 | 11 | v1/imagecache/getlazyresized/lz4-black/480/480/http%3A%2F%2F10.2.1.30%3A1400%2Fgetaa%3Fs%3D1%26u%3Dx-sonos-http%253alibrarytrack%25253ai.8WdG64vCRvYXZ7.mp4%253fsid%253d204%2526flags%253d8224%2526sn%253d1 12 | 13 | 14 | v1/imagecache/getlazyresized/lz4-black/480/480/http%3A%2F%2F10.2.1.30%3A1400%2Fgetaa%3Fs%3D1%26u%3Dx-sonos-http%253alibrarytrack%25253ai.MoxqJEgSkqgZRp.mp4%253fsid%253d204%2526flags%253d8224%2526sn%253d1 15 | 16 | true 17 | 18 | -------------------------------------------------------------------------------- /c.key: -------------------------------------------------------------------------------- 1 | -----BEGIN RSA PRIVATE KEY----- 2 | MIIEpQIBAAKCAQEAr5IBPhPR81TOIxZq/BbQXvgC10CXVrZrk/3fabDwxpYp7Fd5 3 | pg1n7v1kzvHnbk6W8Bklju62mkBujMswx8FPZc46pSE3C5rshss/XcB2ZsYIs+8V 4 | /3QeOUPsjQiFtDzraI0uCo6+50IPz9Gd4kIjfFhf512dX4dZ1+alI9jRnGoVKS5H 5 | pukd2cERymaBqH7/0xiyt3ZMbCzMKsJLsUgHvE9vo+Y/MoVjTDeee3uZtUXki8W/ 6 | esNlvglhpfOPgY5MIpu6CkyvaSP03dGfEiGCxEcX+vhtsa/mJa6M1ezL4gQ6M/RG 7 | WpKHjTse3i7DLO1Kyc5mKucN3VFfghbyo1HnswIDAQABAoIBAEMMezT91Lwcsuxr 8 | b0f+Xm0mQc96d1FCMSs/VMbEL+9nAXOkpGxpyjtWwdzWPQ+/K51dvR4sw8d8u7tB 9 | Dcv7Yxr5+yN838yqyZFgpT5kddMh5cjxkXERI0mzSu9BRe5jJXO0FtUpVnZyoB85 10 | ahYyM+MUzOtKsQL+aa0uA/sAnmwg5InBCydxVNk3YRz6zD/ArPYOOZrdNw+K28uj 11 | D9f93aG1Q2znUczzR7TGqw4dquONc3PEs5I81Z4LU1Rz0cNjc86OsbASmdvjUemQ 12 | LchuWJHMWjEJ2jl99g6JYtU8O7YLVVvR8AVYvaD/dG500oVXsqaHw0kNlbEb4Omc 13 | 804bsMECgYEA58IwENzyamLvRf8owcOWDcj6dJ0XnuhmChqW4cH4CdoKBPQmYJNb 14 | khGs+WhVikS3aEn5v+x8trEWpixO4LjGRxagB1e/i5T42smbgSNlw+V16YgX6iQe 15 | svoEmp6nvo+yubSTQaMxgaTj97XczkbAxbH6Y6YVPANOo7nT+IagAMsCgYEAwe9D 16 | EDOuUiToMXZDbJEbtnDHtmujMHko9Xd9VE0HhCCtNFSQi5AtfiwdkcFalXZH9aMM 17 | XO7J2yrjQLGp2y8tVNmNJTqWh8wtlEfS3aZvzHPRLnm1j8CLWpDZrdJNl+pdfvOV 18 | GpJigae50sXeKNaFoYvq/Cs1auzGM2Zqsf1yX7kCgYEA2WBccRSsE3kkcIT5l3R6 19 | JAfkUsidxSC5xLRX3PxwR91JFIhkDqVoeEM3+N8RjJUTajAonwmTmE/VrJtWiJUG 20 | 9NqV0w1MzgE2wQ/kWWX4J5vr0tUhiS3D1Z+H/fbd43Eo8+IZVLFa1/zvDgJ4Tsoy 21 | ObvL3PeEZzu64PqFhU/Qd60CgYEAm4TOR9DZ6v+zv+5xtT9MdOpODUiV7gpLQUVY 22 | GOFItLkrjHqAC5tMEBE6iScACDl5DU96W5AWCY6D/N48MwvLE27+VCt+iVm/91f9 23 | jkepAdCin910LtoeJjtghJbQKJIF9gdJu6xGGGkziAWq2R7mvJyijSPtS1iivJdV 24 | 2nQ/YukCgYEAptqF67LGUn73Od+tgPIU6SxwnG97BzV899FldNb1FuQMzLhYVeKu 25 | gwDFSip/dmgVW0l7ZXTLadiT+sEAOd6EN5ngZWSebwdfuOsHkitCUFb/U6qRVH/c 26 | FsQYkLuUI9nKeYRLJlX96jmAjzqZ1e8vrca003b00OdPPrbzjQsrQOk= 27 | -----END RSA PRIVATE KEY----- 28 | -------------------------------------------------------------------------------- /http3000.js: -------------------------------------------------------------------------------- 1 | const http = require("http"); 2 | const fs = require("fs"); 3 | const TCP_PORT = 3000; 4 | 5 | const neeoServer = http.createServer((req, res) => { 6 | let responseData = { 7 | code: 200, 8 | headers: { "Content-Type": "text/html; charset=utf-8" }, 9 | content: "" 10 | }; 11 | 12 | const method = req.method; 13 | const headers = req.headers; 14 | const uriparts = decodeURI(req.url).split("/"); 15 | const clientIp = req.connection.remoteAddress.replace(/^.*:/, ""); 16 | 17 | if (req.url.indexOf("/projects/home/tr2/gui_xml") != -1) { 18 | console.log(`gui_xml`); 19 | responseData.content = fs.readFileSync("gui2.xml", "utf8"); 20 | //responseData.content = gui.xml(); 21 | responseData.content = responseData.content + ""; 22 | /* responseData.headers = { 23 | "Content-Type": "text/html; charset=utf-8", 24 | ETag: 'W/"bac5-hA8bJH0nxN91ku7gUb5/RwIGpEg"', 25 | "Access-Control-Allow-Methods": "POST, GET, PUT, DELETE, OPTIONS", 26 | "Access-Control-Allow-Headers": "Content-Type,Accept,X-Requested-With,Origin,X-NEEO-Secure", 27 | "Access-Control-Allow-Credentials": "true" 28 | }; */ 29 | } else if (req.url.indexOf("/projects/checkAirkey") != -1) { 30 | /* responseData.headers = { 31 | "Content-Type": "text/html; charset=utf-8", 32 | ETag: 'W/"2-nOO9QiTIwXgNtWtBJezz8kv3SLc"', 33 | "Access-Control-Allow-Methods": "POST, GET, PUT, DELETE, OPTIONS", 34 | "Access-Control-Allow-Headers": "Content-Type,Accept,X-Requested-With,Origin,X-NEEO-Secure", 35 | "Access-Control-Allow-Credentials": "true" 36 | }; */ 37 | responseData.content = "OK"; 38 | } else if (req.url.indexOf("/neeo.xml") != -1) { 39 | responseData.content = fs.readFileSync("neeo.xml", "utf8"); 40 | } else if (req.url.indexOf("/projects/home/tr2/guidata_xml") != -1) { 41 | console.log(`guidata_xml`); 42 | responseData.content = fs.readFileSync("guidata.xml", "utf8"); 43 | } else if (req.url.indexOf("/v1/imagecache/") != -1) { 44 | //console.log(`imgcache not implemented...`); 45 | } else if (req.method == "POST") { 46 | let body = ""; 47 | req.on("data", function(data) { 48 | body += data; 49 | }); 50 | req.on("end", function() { 51 | //console.log(`POST: ${body}`); 52 | }); 53 | } else { 54 | console.log(`Port: ${TCP_PORT}`); 55 | console.log(`Method: ${method}`); 56 | console.log(`url: ${req.url}`); 57 | console.log(`clientIp: ${clientIp}`); 58 | console.log(`Response L: ${responseData.content.length}`); 59 | console.log(``); 60 | } 61 | 62 | ///v1/imagecache/ 63 | 64 | //res.writeHead(responseData.code, responseData.headers); 65 | //res.write(responseData.content); 66 | res.end(responseData.content); 67 | }); 68 | 69 | neeoServer.listen(TCP_PORT, function() { 70 | console.log("N330 TCP service running on: TCP/" + TCP_PORT); 71 | }); 72 | -------------------------------------------------------------------------------- /gui2.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 |
20 | 21 | 22 | 23 | 24 | 25 | 26 |
27 | 28 | 29 | 30 | 31 | 32 | 33 | 34 | 35 | 36 | 37 | 38 | 39 | 40 | 41 | 42 | 43 | 44 | 45 | 46 | 47 | 48 | 49 | 50 | 51 | 52 |