diff --git a/.gitignore b/.gitignore index cde69dcc..5436205d 100644 --- a/.gitignore +++ b/.gitignore @@ -366,3 +366,4 @@ FodyWeavers.xsd /zefie_wtvp_minisrv/ServiceVault/wtv-home/6969.html /zefie_wtvp_minisrv/user_config.json /zefie_wtvp_minisrv/ServiceVault/wtv-home/home.zefie.html +/zefie_wtvp_minisrv/UserServiceVault/wtv-update diff --git a/zefie_wtvp_minisrv/.gitignore b/zefie_wtvp_minisrv/.gitignore index 0dade07a..1c8fb1f0 100644 --- a/zefie_wtvp_minisrv/.gitignore +++ b/zefie_wtvp_minisrv/.gitignore @@ -7,6 +7,7 @@ ServiceLogPost/*_* # Large files not pertaining to the service code +UserServiceVault/*-* ServiceVault/wtv-flashrom/content/* ServiceVault/wtv-music/content/* ServiceVault/wtv-music/midi/* @@ -368,4 +369,4 @@ MigrationBackup/ # Fody - auto-generated XML schema FodyWeavers.xsd -/hacktv_updsrv/ServiceLogPost/1626307222_warning_812bf30600b002bb + diff --git a/zefie_wtvp_minisrv/ServiceVault/wtv-1800/finish-prereg.js b/zefie_wtvp_minisrv/ServiceVault/wtv-1800/finish-prereg.js index 809212a0..b51ac449 100644 --- a/zefie_wtvp_minisrv/ServiceVault/wtv-1800/finish-prereg.js +++ b/zefie_wtvp_minisrv/ServiceVault/wtv-1800/finish-prereg.js @@ -24,7 +24,8 @@ if (wtvsec_login) { switch (romtype) { case "US-LC2-disk-0MB-8MB": prereg_contype = "text/tellyscript"; - var file_path = __dirname + "/ServiceDeps/premade_tellyscripts/LC2/LC2_OISP_5555732_56k.tok"; + if (ssid_sessions[socket.ssid].get("wtv-open-access")) var file_path = __dirname + "/ServiceDeps/premade_tellyscripts/LC2/LC2_OISP_5555732_56k.tok"; + else var file_path = __dirname + "/ServiceDeps/premade_tellyscripts/LC2/LC2_WTV_18006138199_56k.tok"; break; default: diff --git a/zefie_wtvp_minisrv/ServiceVault/wtv-home/home.js b/zefie_wtvp_minisrv/ServiceVault/wtv-home/home.js index 024f3807..6d737a3d 100644 --- a/zefie_wtvp_minisrv/ServiceVault/wtv-home/home.js +++ b/zefie_wtvp_minisrv/ServiceVault/wtv-home/home.js @@ -28,8 +28,9 @@ data += `

Working stuff

` diff --git a/zefie_wtvp_minisrv/ServiceVault/wtv-music/demo/index.html b/zefie_wtvp_minisrv/ServiceVault/wtv-music/demo/index.html index 3b66cfda..95c06be6 100644 --- a/zefie_wtvp_minisrv/ServiceVault/wtv-music/demo/index.html +++ b/zefie_wtvp_minisrv/ServiceVault/wtv-music/demo/index.html @@ -5,7 +5,7 @@ WebTV Music Index - + diff --git a/zefie_wtvp_minisrv/ServiceVault/wtv-update/update.html b/zefie_wtvp_minisrv/ServiceVault/wtv-update/DealerDemo.html similarity index 55% rename from zefie_wtvp_minisrv/ServiceVault/wtv-update/update.html rename to zefie_wtvp_minisrv/ServiceVault/wtv-update/DealerDemo.html index 7c2cf193..263a2a20 100644 --- a/zefie_wtvp_minisrv/ServiceVault/wtv-update/update.html +++ b/zefie_wtvp_minisrv/ServiceVault/wtv-update/DealerDemo.html @@ -2,23 +2,23 @@ - - HackTV Updater + + Retrieving Files
- +
- Download HackTV Updates + Retrieving Files
@@ -30,17 +30,17 @@
- - Your HackTV Unit is downloading updates. -

This may take a while. - + + Your Internet terminal is retrieving some files. +

This may take a while. +



diff --git a/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/DealerDemo/allyouneed.html b/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/DealerDemo/allyouneed.html new file mode 100644 index 00000000..55922b5c --- /dev/null +++ b/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/DealerDemo/allyouneed.html @@ -0,0 +1,15 @@ + + +Shockwave + + + + + + +
+ + +
+ + diff --git a/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/DealerDemo/allyouneed.swf b/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/DealerDemo/allyouneed.swf new file mode 100644 index 00000000..2500fb7a Binary files /dev/null and b/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/DealerDemo/allyouneed.swf differ diff --git a/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/DealerDemo/attractloop.swf b/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/DealerDemo/attractloop.swf new file mode 100644 index 00000000..d906a72e Binary files /dev/null and b/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/DealerDemo/attractloop.swf differ diff --git a/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/DealerDemo/communicate.html b/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/DealerDemo/communicate.html new file mode 100644 index 00000000..5e785ff9 --- /dev/null +++ b/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/DealerDemo/communicate.html @@ -0,0 +1,15 @@ + + +Shockwave + + + + + + +
+ + +
+ + diff --git a/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/DealerDemo/communicate.swf b/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/DealerDemo/communicate.swf new file mode 100644 index 00000000..a48c2adb Binary files /dev/null and b/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/DealerDemo/communicate.swf differ diff --git a/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/DealerDemo/images/buttonsplus_all.gif b/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/DealerDemo/images/buttonsplus_all.gif new file mode 100644 index 00000000..c94d1724 Binary files /dev/null and b/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/DealerDemo/images/buttonsplus_all.gif differ diff --git a/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/DealerDemo/images/buttonsplus_comm.gif b/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/DealerDemo/images/buttonsplus_comm.gif new file mode 100644 index 00000000..4594076c Binary files /dev/null and b/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/DealerDemo/images/buttonsplus_comm.gif differ diff --git a/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/DealerDemo/images/buttonsplus_interactive.gif b/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/DealerDemo/images/buttonsplus_interactive.gif new file mode 100644 index 00000000..7390bf5a Binary files /dev/null and b/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/DealerDemo/images/buttonsplus_interactive.gif differ diff --git a/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/DealerDemo/images/buttonsplus_internet.gif b/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/DealerDemo/images/buttonsplus_internet.gif new file mode 100644 index 00000000..05c136dd Binary files /dev/null and b/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/DealerDemo/images/buttonsplus_internet.gif differ diff --git a/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/DealerDemo/images/buttonsplus_try.gif b/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/DealerDemo/images/buttonsplus_try.gif new file mode 100644 index 00000000..8f977b92 Binary files /dev/null and b/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/DealerDemo/images/buttonsplus_try.gif differ diff --git a/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/DealerDemo/images/spacer.gif b/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/DealerDemo/images/spacer.gif new file mode 100644 index 00000000..5bfd67a2 Binary files /dev/null and b/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/DealerDemo/images/spacer.gif differ diff --git a/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/DealerDemo/index.html b/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/DealerDemo/index.html new file mode 100644 index 00000000..e9328216 --- /dev/null +++ b/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/DealerDemo/index.html @@ -0,0 +1,15 @@ + + +Shockwave + + + + + + +
+ + +
+ + diff --git a/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/DealerDemo/interactive.html b/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/DealerDemo/interactive.html new file mode 100644 index 00000000..7e6a2f8c --- /dev/null +++ b/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/DealerDemo/interactive.html @@ -0,0 +1,15 @@ + + +Shockwave + + + + + + +
+ + +
+ + diff --git a/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/DealerDemo/interactive.swf b/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/DealerDemo/interactive.swf new file mode 100644 index 00000000..e85a85eb Binary files /dev/null and b/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/DealerDemo/interactive.swf differ diff --git a/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/DealerDemo/internet.html b/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/DealerDemo/internet.html new file mode 100644 index 00000000..fa7f4c73 --- /dev/null +++ b/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/DealerDemo/internet.html @@ -0,0 +1,15 @@ + + +Shockwave + + + + + + +
+ + +
+ + diff --git a/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/DealerDemo/internet.swf b/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/DealerDemo/internet.swf new file mode 100644 index 00000000..9e30d55c Binary files /dev/null and b/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/DealerDemo/internet.swf differ diff --git a/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/DealerDemo/mainmenu.html b/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/DealerDemo/mainmenu.html new file mode 100644 index 00000000..abbb3d42 --- /dev/null +++ b/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/DealerDemo/mainmenu.html @@ -0,0 +1,61 @@ + + +Shockwave + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
+ + \ No newline at end of file diff --git a/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/DealerDemo/mainmenu.swf b/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/DealerDemo/mainmenu.swf new file mode 100644 index 00000000..31fdcade Binary files /dev/null and b/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/DealerDemo/mainmenu.swf differ diff --git a/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/DealerDemo/trymsntv.html b/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/DealerDemo/trymsntv.html new file mode 100644 index 00000000..dddf1902 --- /dev/null +++ b/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/DealerDemo/trymsntv.html @@ -0,0 +1,15 @@ + + +Shockwave + + + + + + +
+ + +
+ + diff --git a/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/DealerDemo/trymsntv.swf b/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/DealerDemo/trymsntv.swf new file mode 100644 index 00000000..214df710 Binary files /dev/null and b/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/DealerDemo/trymsntv.swf differ diff --git a/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/diskmaps/DealerDemo.json b/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/diskmaps/DealerDemo.json new file mode 100644 index 00000000..8cf6c689 --- /dev/null +++ b/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/diskmaps/DealerDemo.json @@ -0,0 +1,70 @@ +{ + "DealerDemo": { + "display": "Updating the retail demo", + "base": "file://Disk/Demo/", + "location": "content/DealerDemo/", + "partition_size": 54525952, + "files": [ + { + "file": "file://Disk/Demo/allyouneed.html" + }, + { + "file": "file://Disk/Demo/allyouneed.swf" + }, + { + "file": "file://Disk/Demo/attractloop.swf" + }, + { + "file": "file://Disk/Demo/communicate.html" + }, + { + "file": "file://Disk/Demo/communicate.swf" + }, + { + "file": "file://Disk/Demo/images/buttonsplus_all.gif" + }, + { + "file": "file://Disk/Demo/images/buttonsplus_comm.gif" + }, + { + "file": "file://Disk/Demo/images/buttonsplus_interactive.gif" + }, + { + "file": "file://Disk/Demo/images/buttonsplus_internet.gif" + }, + { + "file": "file://Disk/Demo/images/buttonsplus_try.gif" + }, + { + "file": "file://Disk/Demo/images/spacer.gif" + }, + { + "file": "file://Disk/Demo/index.html" + }, + { + "file": "file://Disk/Demo/interactive.html" + }, + { + "file": "file://Disk/Demo/interactive.swf" + }, + { + "file": "file://Disk/Demo/internet.html" + }, + { + "file": "file://Disk/Demo/internet.swf" + }, + { + "file": "file://Disk/Demo/mainmenu.html" + }, + { + "file": "file://Disk/Demo/mainmenu.swf" + }, + { + "file": "file://Disk/Demo/trymsntv.html" + }, + { + "file": "file://Disk/Demo/trymsntv.swf" + } + ] + } +} \ No newline at end of file diff --git a/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/diskmaps/htvupdate.txt b/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/diskmaps/htvupdate.txt deleted file mode 100644 index d2d97268..00000000 --- a/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/diskmaps/htvupdate.txt +++ /dev/null @@ -1,10 +0,0 @@ -GROUP name=Browser version=!VERS! root=file://Disk/Browser/Games/ - display Updating HackTV Files... - sync Games.html content/htvupdate/Games/Games.html - sync cSetup.html content/htvupdate/Games/cSetup.html -END-GROUP - -GROUP name=Browser version=!VERS! root=file://Disk/Browser/MattMan/ - display Updating HackTV Files... - sync Tricks/tricks.html content/htvupdate/MattMan/Tricks/tricks.html -END-GROUP \ No newline at end of file diff --git a/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/htvupdate/Games/Games.html b/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/htvupdate/Games/Games.html deleted file mode 100644 index a76fca83..00000000 --- a/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/htvupdate/Games/Games.html +++ /dev/null @@ -1,122 +0,0 @@ - - -HackTV Home - - - - - - - -

-

-
- - - - - - - - - - -
  - - - - - - - - - - - - - - - - -
Play Games
-
  • M.A.M.E. -
  • Doom - -
  • Checkers -
  • Crosswords -
  • TicTacToe
  • Play Music
    -
  • WebTV Music -
  • Rock Music
  • Tech Area
    -
  • Tech Info -
  • HTML Viewer -
  • HackTV Tricks -
  • Connect Setup -
  • NEW! Check for Updates - -
  • -
    - - - - - -
    -
    -&date;

    -wtv -
    - - - - -
    -
    - - - - - -
    - -
    -
    - - \ No newline at end of file diff --git a/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/htvupdate/Games/cSetup.html b/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/htvupdate/Games/cSetup.html deleted file mode 100644 index a8399225..00000000 --- a/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/htvupdate/Games/cSetup.html +++ /dev/null @@ -1,143 +0,0 @@ - - -Connect Setup v2.1 - - - - - - - - - -

    -

    -
    - - -

    -  Connection Setup v2.1 -
    -

    - -
    - - - - - - - - -
    -  Presets: - - -
    -  Service: -
    -
    -
    - - - -  Custom:    - - Address: - -    Port: - -
    - - - - - - - - -
    -
    -  Service options:

    -
    - - - -  Force signup - - -   -   - - -
    -
    - - - -  Use encryption -
    -
    - - - -  Use direct connection - -   -   - -
    -

    - - -
    - - - -
    - - - - diff --git a/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/htvupdate/MattMan/Tricks/tricks.html b/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/htvupdate/MattMan/Tricks/tricks.html deleted file mode 100644 index e714ca78..00000000 --- a/zefie_wtvp_minisrv/ServiceVault/wtv-update/content/htvupdate/MattMan/Tricks/tricks.html +++ /dev/null @@ -1,52 +0,0 @@ - - -HackTV Tricks - - - - - - - - -
    -
    -
    -

    HackTV Tricks

    -
    -
    -Hello, citizen! You have reached the "tricks" page. This is meant -for use by 1337 hackers of WebTV networks. If you remember the -right "tricks" you know the password and may enter the access password now. -Otherwise hit the "back" button on your keyboard / remote now! -

    -Pages beyond this area could cause bodily harm or may render your WebTV useless! -

    -Remember, the computer is your friend. -

    - -

    -  - - -
    - - - \ No newline at end of file diff --git a/zefie_wtvp_minisrv/ServiceVault/wtv-update/sync.js b/zefie_wtvp_minisrv/ServiceVault/wtv-update/sync.js index 36b4445f..9328724b 100644 --- a/zefie_wtvp_minisrv/ServiceVault/wtv-update/sync.js +++ b/zefie_wtvp_minisrv/ServiceVault/wtv-update/sync.js @@ -1,41 +1,176 @@ -// todo: async (and make this work anyway) +// todo: async -var content_dir = service_dir + '/content/'; -var diskmap_dir = content_dir + '/diskmaps/'; +var path = require("path"); -if (request_headers.post_data) { - console.log(request_headers.post_data.toString('CryptoJS.enc.Latin1')) +var content_dir = "content/" +var diskmap_dir = content_dir + "diskmaps/"; + +function generateDownloadList(diskmap_group_data, update_list, diskmap_data) { + // create WebTV Download List + + var newest_file_epoch = 0; + var download_list = ''; + + if (diskmap_data.partition_size) { + download_list += "CREATE " + diskmap_data.base + "\n"; + download_list += "partition-size: " + diskmap_data.partition_size + "\n\n"; + } + + download_list += "CREATE-GROUP " + diskmap_group_data + "-UPDATE\n"; + download_list += "state: invalid\n"; + download_list += "base: " + diskmap_data.base + ".GROUP-UPDATE/\n\n"; + + Object.keys(update_list).forEach(function (k) { + if (parseInt(update_list[k]["Last-modified"]) > newest_file_epoch) newest_file_epoch = parseInt(update_list[k]["Last-modified"]); + download_list += "DISPLAY " + update_list[k].display + "\n\n"; + download_list += "GET " + update_list[k].file.replace(diskmap_data.base, "") + "\n"; + download_list += "group: " + diskmap_group_data + "-UPDATE\n"; + download_list += "location: " + service_name + ":/" + update_list[k].location + "\n"; + download_list += "file-permission: r\n" + download_list += "wtv-checksum: " + update_list[k]["wtv-checksum"] + "\n"; + download_list += "service-source-location: /webtv/content/" + service_name.replace("wtv-","") + "d/" + update_list[k].location + "\n"; + download_list += "client-dest-location: " + update_list[k].file + "\n\n"; + }); + + download_list += "CREATE-GROUP " + diskmap_group_data + "\n"; + download_list += "state: invalid\n"; + download_list += "service-owned: " + (diskmap_data.service_owned || false) + "\n"; + download_list += "base: " + diskmap_data.base + "\n\n"; + + Object.keys(update_list).forEach(function (k) { + download_list += "DELETE " + update_list[k].file.replace(diskmap_data.base, "") + "\n"; + download_list += "group: " + diskmap_group_data + "\n\n"; + }); + + Object.keys(update_list).forEach(function (k) { + download_list += "RENAME " + update_list[k].file.replace(diskmap_data.base, "") + "\n"; + download_list += "group: " + diskmap_group_data + "-UPDATE\n"; + download_list += "destination-group: " + diskmap_group_data + "\n"; + download_list += "location: " + update_list[k].file.replace(diskmap_data.base, "") + "\n\n"; + }); + + download_list += "DELETE-GROUP " + diskmap_group_data + "-UPDATE\n\n"; + + download_list += "SET-GROUP " + diskmap_group_data + "\n"; + download_list += "state: ok\n"; + download_list += "version: " + newest_file_epoch + "\n"; + download_list += "last-checkup-time: " + new Date().toUTCString().replace("GMT", "+0000") + "\n\n"; + + return download_list; } -if (request_headers.query.diskmap) { - if (fs.lstatSync(diskmap_dir + request_headers.query.diskmap + ".txt")) { - var diskmap_data = fs.readFileSync(diskmap_dir + request_headers.query.diskmap + ".txt").toString(); - // try to parse diskmap and get an accurate timestamp for webtv versioning - // check all files in the diskmap and return the timestamp of the most recently modified +function processGroup(diskmap_primary_group, diskmap_group_data, diskmap_subgroup = null) { + // parse webtv post + var output_data = ''; + var post_data = request_headers.post_data.toString(CryptoJS.enc.Latin1).split("\n"); + var post_data_current_directory = ''; + var post_data_current_file = ''; + var post_data_fileinfo = new Array(); + var post_data_filecount = -1; - data = ''; - var latest_file_ts = 0; - diskmap_data.split("\n").forEach(function (v) { - if (v.indexOf(" sync ") != -1) { - v = v.trim(); - var vcon = v.substring(v.indexOf("content/")); - vcon = vcon.replace("content/", content_dir) - var vconstat = Math.floor(fs.lstatSync(vcon).mtimeMs / 1000); - if (vconstat > latest_file_ts) { - latest_file_ts = vconstat - } - // todo read client post and only give whats needed - // instead of all that is available - // vconstat has the mtime of each file, we need to parse the post_data - data += v + "\n"; - } else { - data += v + "\n"; + Object.keys(post_data).forEach(function (k) { + if (post_data[k] == "") return; + if (post_data[k].substring(0, 7) == "file://") { + post_data_current_directory = post_data[k]; + post_data_current_file = post_data[k]; + } + if (post_data[k].indexOf(":") > 0) { + var post_data_line = post_data[k].split(":") + var post_data_line_name = post_data_line[0]; + post_data_line.shift(); + var post_data_line_data = post_data_line.join(":"); + + if (!post_data_fileinfo[post_data_filecount]) post_data_fileinfo[post_data_filecount] = new Array(); + + if (post_data_line_name == "Last-modified") { + post_data_fileinfo[post_data_filecount][post_data_line_name] = (Date.parse(post_data_line_data) / 1000); + } else if (post_data_line_name == "Content-length") { + post_data_fileinfo[post_data_filecount][post_data_line_name] = parseInt(post_data_line_data); } + else { + post_data_fileinfo[post_data_filecount][post_data_line_name] = post_data_line_data; + } + + + } else { + post_data_filecount++; + post_data_current_file = post_data_current_directory + post_data[k]; + post_data_fileinfo[post_data_filecount] = new Array(); + post_data_fileinfo[post_data_filecount].file = post_data_current_file + } + }); + var wtv_download_list = new Array(); + Object.keys(diskmap_group_data.files).forEach(function (k) { + if (!diskmap_group_data.files[k].location) diskmap_group_data.files[k].location = diskmap_group_data.location + diskmap_group_data.files[k].file.replace(diskmap_group_data.base, ""); + var post_match_file = null; + Object.keys(service_vaults).forEach(function (g) { + if (post_match_file != null) return; + post_match_file = service_vaults[g].path + "/" + service_name + "/" + diskmap_group_data.files[k].location; + if (!fs.existsSync(post_match_file)) post_match_file = null; }); - //data = diskmap_data.replace("!VERS!", latest_file_ts); + var post_match_file_lstat = fs.lstatSync(post_match_file); + var post_match_result = post_data_fileinfo.find(el => el["file"] === diskmap_group_data.files[k].file) || false; + var post_match_file_data = new Buffer.from(fs.readFileSync(post_match_file, { + encoding: null, + flags: 'r' + })); + diskmap_group_data.files[k]["Last-modified"] = (post_match_file_lstat.mtime / 1000); + diskmap_group_data.files[k]["Content-length"] = post_match_file_lstat.size; + diskmap_group_data.files[k]["wtv-checksum"] = CryptoJS.MD5(CryptoJS.lib.WordArray.create(post_match_file_data)).toString(CryptoJS.enc.Hex).toLowerCase(); + if (!diskmap_group_data.files[k].display) diskmap_group_data.files[k].display = diskmap_group_data.display; + + if (post_match_result) { + // md5s match, so client doesn't need file + if (diskmap_group_data.files[k]['wtv-checksum'] == post_match_result["wtv-checksum"]) return; + else wtv_download_list.push(diskmap_group_data.files[k]); + } else { + wtv_download_list.push(diskmap_group_data.files[k]); + } + var diskmap_group_name = (diskmap_subgroup == null) ? diskmap_primary_group : diskmap_primary_group + "-" + diskmap_subgroup; + output_data = generateDownloadList(diskmap_group_name, wtv_download_list, diskmap_group_data) + }); + return output_data; +} + +if (request_headers.query.diskmap && request_headers.query.group && request_headers.post_data) { + var diskmap_json_file = null; + Object.keys(service_vaults).forEach(function (g) { + if (diskmap_json_file != null) return; + diskmap_json_file = service_vaults[g].path + "/" + service_name + "/" + diskmap_dir + request_headers.query.diskmap + ".json"; + if (!fs.existsSync(diskmap_json_file)) diskmap_json_file = null; + }); + + if (diskmap_json_file != null) { + if (fs.lstatSync(diskmap_json_file)) { + try { + // read diskmap + var diskmap_data = JSON.parse(fs.readFileSync(diskmap_json_file).toString()); + if (!diskmap_data[request_headers.query.group]) { + throw ("Invalid diskmap data (group does not match)"); + } + data = ''; + diskmap_data = diskmap_data[request_headers.query.group]; + /*if (!diskmap_data.display) { + Object.keys(diskmap_data).forEach(function (k) { + if (diskmap_data[k]) data += processGroup(request_headers.query.group,diskmap_data[k],k); + }); + } else { */ + data = processGroup(request_headers.query.group, diskmap_data); + //} + + headers = "200 OK\nContent-Type: wtv/download-list"; + } catch (e) { + var errpage = doErrorPage(400); + headers = errpage[0]; + data = errpage[1]; + console.log("wtv-update:/sync error", e); + } + } + } else { + var errpage = doErrorPage(404,"The requested DiskMap does not exist."); + headers = errpage[0]; + data = errpage[1]; + console.log("wtv-update:/sync error", "could not find diskmap"); } } -headers = `200 OK -Content-type: text/download-list` - diff --git a/zefie_wtvp_minisrv/UserServiceVault/anything you put in here has priority.txt b/zefie_wtvp_minisrv/UserServiceVault/anything you put in here has priority.txt new file mode 100644 index 00000000..e69de29b diff --git a/zefie_wtvp_minisrv/app.js b/zefie_wtvp_minisrv/app.js index fc1d385e..18a9db91 100644 --- a/zefie_wtvp_minisrv/app.js +++ b/zefie_wtvp_minisrv/app.js @@ -13,8 +13,6 @@ var ClientSessionData = require('./session_data.js'); var ports = []; -var service_vault_dir = __dirname + "/ServiceVault"; - String.prototype.reverse = function () { var splitString = this.split(""); var reverseArray = splitString.reverse(); @@ -87,92 +85,77 @@ async function processPath(socket, path, request_headers = new Array(), service_ var headers, data = null; var request_is_direct_file = false; var request_is_async = false; - path = path.replace(/\\/g, "/"); + var service_vault_found = false; + var service_path = path; try { - try { - // try to see if the exact request exists - if (fs.lstatSync(path).isFile()) { - request_is_direct_file = true; + service_vaults.forEach(function (service_vault_dir) { + if (service_vault_found) return; + path = service_vault_dir.path + "/" + service_path.replace(/\\/g, "/"); + + + if (fs.existsSync(path)) { + // file exists, read it and return it + service_vault_found = true; + request_is_async = true; + if (!zquiet) console.log(" * Found " + path + " in " + service_vault_dir.name +" to handle request (Direct File Mode) [Socket " + socket.id + "]"); + var contype = getConType(path); + headers = "200 OK\n" + headers += "Content-Type: " + contype; + fs.readFile(path, null, function (err, data) { + sendToClient(socket, headers, data); + }); + } else if (fs.existsSync(path + ".txt")) { + service_vault_found = true; + // raw text format, entire payload expected (headers and content) + if (!zquiet) console.log(" * Found " + path + ".txt in " + service_vault_dir.name +" to handle request (Raw TXT Mode) [Socket " + socket.id + "]"); + request_is_async = true; + fs.readFile(path + ".txt", 'Utf-8', function (err, file_raw) { + if (file_raw.indexOf("\n\n") > 0) { + // split headers and data by newline (unix format) + var file_raw_split = file_raw.split("\n\n"); + headers = file_raw_split[0]; + file_raw_split.shift(); + data = file_raw_split.join("\n"); + } else if (file_raw.indexOf("\r\n\r\n") > 0) { + // split headers and data by carrage return + newline (windows format) + var file_raw_split = file_raw.split("\r\n\r\n"); + headers = file_raw_split[0].replace(/\r/g, ""); + file_raw_split.shift(); + data = file_raw_split.join("\r\n"); + } else { + // couldn't find two line breaks, assume entire file is just headers + headers = file_raw; + data = ''; + } + sendToClient(socket, headers, data); + }); + } else if (fs.existsSync(path + ".js")) { + service_vault_found = true; + // synchronous js scripting, process with vars, must set 'headers' and 'data' appropriately. + // loaded script will have r/w access to any JavaScript vars this function does. + // request headers are in an array named `request_headers`. + // Query arguments in `request_headers.query` + if (!zquiet) console.log(" * Found " + path + ".js in " + service_vault_dir.name + " to handle request (JS Interpreter mode) [Socket " + socket.id + "]"); + // expose var service_dir for script path to the root of the wtv-service + var service_dir = service_vault_dir.path.replace(/\\/g, "/") + "/" + service_name; + socket_sessions[socket.id].starttime = Math.floor(new Date().getTime() / 1000); + var jscript_eval = fs.readFileSync(path + ".js").toString(); + eval(jscript_eval); + if (request_is_async && !zquiet) console.log(" * Script requested Asynchronous mode"); } - } catch (e) { - // do nothing its fine - } - - if (request_is_direct_file) { - // file exists, read it and return it - if (!zquiet) console.log(" * Found " + path + " to handle request (Direct File Mode) [Socket " + socket.id +"]"); - var contype = getConType(path); - request_is_async = true; - headers = "200 OK\n" - headers += "Content-Type: " + contype; - fs.readFile(path, null, function (err, data) { - sendToClient(socket, headers, data); - }); - } else if (fs.existsSync(path + ".txt")) { - // raw text format, entire payload expected (headers and content) - if (!zquiet) console.log(" * Found " + path + ".txt to handle request (Raw TXT Mode) [Socket " + socket.id + "]"); - request_is_async = true; - fs.readFile(path + ".txt", 'Utf-8', function (err, file_raw) { - if (file_raw.indexOf("\n\n") > 0) { - // split headers and data by newline (unix format) - var file_raw_split = file_raw.split("\n\n"); - headers = file_raw_split[0]; - file_raw_split.shift(); - data = file_raw_split.join("\n"); - } else if (file_raw.indexOf("\r\n\r\n") > 0) { - // split headers and data by carrage return + newline (windows format) - var file_raw_split = file_raw.split("\r\n\r\n"); - headers = file_raw_split[0].replace(/\r/g, ""); - file_raw_split.shift(); - data = file_raw_split.join("\r\n"); - } else { - // couldn't find two line breaks, assume entire file is just headers - headers = file_raw; - data = ''; - } - sendToClient(socket, headers, data); - }); - } else if (fs.existsSync(path + ".js")) { - // synchronous js scripting, process with vars, must set 'headers' and 'data' appropriately. - // loaded script will have r/w access to any JavaScript vars this function does. - // request headers are in an array named `request_headers`. - // Query arguments in `request_headers.query` - if (!zquiet) console.log(" * Found " + path + ".js to handle request (JS Interpreter mode) [Socket " + socket.id + "]"); - // expose var service_dir for script path to the root of the wtv-service - var service_dir = service_vault_dir.replace(/\\/g, "/") + "/" + service_name; - socket_sessions[socket.id].starttime = Math.floor(new Date().getTime() / 1000); - var jscript_eval = fs.readFileSync(path + ".js").toString(); - eval(jscript_eval); - if (request_is_async && !zquiet) console.log(" * Script requested Asynchronous mode"); - } - else if (fs.existsSync(path + ".html")) { - // Standard HTML with no headers, WTV Style - if (!zquiet) console.log(" * Found " + path + ".html to handle request (HTML Mode) [Socket " + socket.id +"]"); - request_is_async = true; - headers = "200 OK\n" - headers += "Content-Type: text/html" - fs.readFile(path + ".html", null, function (err, data) { - sendToClient(socket, headers, data); - }); - } else { - var errpage = doErrorPage(404); - headers = errpage[0]; - data = errpage[1]; - } - - // 'headers' and 'data' should both be set with content by this point! - - - if (headers == null && !request_is_async) { - var errpage = doErrorPage(400); - headers = errpage[0]; - data = errpage[1]; - console.log(" * Scripting or Data error: Headers were not defined. (headers,data) as follows:") - console.log(socket.id,headers,data) - } - if (data === null) { - data = ''; - } + else if (fs.existsSync(path + ".html")) { + service_vault_found = true; + // Standard HTML with no headers, WTV Style + if (!zquiet) console.log(" * Found " + path + ".html in " + service_vault_dir.name +" to handle request (HTML Mode) [Socket " + socket.id + "]"); + request_is_async = true; + headers = "200 OK\n" + headers += "Content-Type: text/html" + fs.readFile(path + ".html", null, function (err, data) { + sendToClient(socket, headers, data); + }); + } + // 'headers' and 'data' should both be set with content by this point! + }); } catch (e) { var errpage = doErrorPage(400); headers = errpage[0]; @@ -180,6 +163,22 @@ async function processPath(socket, path, request_headers = new Array(), service_ console.log(" * Scripting error:",e); } if (!request_is_async) { + if (!service_vault_found) { + console.log(" * Could not find a Service Vault for", service_path); + var errpage = doErrorPage(404); + headers = errpage[0]; + data = errpage[1]; + } + if (headers == null && !request_is_async) { + var errpage = doErrorPage(400); + headers = errpage[0]; + data = errpage[1]; + console.log(" * Scripting or Data error: Headers were not defined. (headers,data) as follows:") + console.log(socket.id, headers, data) + } + if (data === null) { + data = ''; + } sendToClient(socket, headers, data); } } @@ -250,7 +249,7 @@ async function processURL(socket, request_headers) { } // assume webtv since there is a :/ in the GET var service_name = shortURL.split(':/')[0]; - var urlToPath = service_vault_dir.replace(/\\/g, "/") + "/" + service_name + "/" + shortURL.split(':/')[1]; + var urlToPath = service_name + "/" + shortURL.split(':/')[1]; if (zshowheaders) console.log(" * Incoming headers on socket ID", socket.id, (await processSSID(request_headers))); processPath(socket, urlToPath, request_headers, service_name); } else if (shortURL.indexOf('http://') >= 0 || shortURL.indexOf('https://') >= 0) { @@ -530,7 +529,7 @@ function headersAreStandard(string, verbose = false) { async function processRequest(socket, data_hex, returnHeadersBeforeSecure = false, encryptedRequest = false) { var url = ""; - var data = CryptoJS.enc.Latin1.stringify(CryptoJS.enc.Hex.parse(data_hex)); + var data = Buffer.from(data_hex,'hex').toString('ascii'); var headers = new Array(); if (typeof data === "string") { @@ -556,6 +555,14 @@ async function processRequest(socket, data_hex, returnHeadersBeforeSecure = fals } var enc_data = CryptoJS.enc.Hex.parse(data_hex.substring(header_length * 2)); if (enc_data.sigBytes > 0) { + if (!socket_sessions[socket.id].wtvsec) { + var errpage = doErrorPage(400); + headers = errpage[0]; + headers += "wtv-visit: client:relog\n"; + data = errpage[1]; + sendToClient(socket, headers, data); + return; + } var dec_data = CryptoJS.lib.WordArray.create(socket_sessions[socket.id].wtvsec.Decrypt(0, enc_data)); var secure_headers = await processRequest(socket, dec_data.toString(CryptoJS.enc.Hex), true, true); headers.encrypted = true; @@ -570,6 +577,8 @@ async function processRequest(socket, data_hex, returnHeadersBeforeSecure = fals socket.ssid = headers["wtv-client-serial-number"]; if (!ssid_sessions[socket.ssid]) { ssid_sessions[socket.ssid] = new ClientSessionData(); + ssid_sessions[socket.ssid].sockets = new Array(); + ssid_sessions[socket.ssid].sockets.push(socket.id); } } @@ -592,7 +601,7 @@ async function processRequest(socket, data_hex, returnHeadersBeforeSecure = fals return headers; } - if (headers.secure === true) { + if (headers.secure === true || headers.encrypted === true) { if (!socket_sessions[socket.id].wtvsec) { if (!zquiet) console.log(" * Starting new WTVSec instance on socket", socket.id); if (ssid_sessions[socket.ssid].get("wtv-incarnation")) { @@ -636,7 +645,7 @@ async function processRequest(socket, data_hex, returnHeadersBeforeSecure = fals if (zdebug) console.log(" # Encrypted Request (SECURE ON)", "on", socket.id, secure_headers); if (!secure_headers.request) { socket_sessions[socket.id].secure = false; - var errpage = doErrorPage(499, "Security Stream Busted"); + var errpage = doErrorPage(400); headers = errpage[0]; data = errpage[1]; sendToClient(socket, headers, data); @@ -649,8 +658,9 @@ async function processRequest(socket, data_hex, returnHeadersBeforeSecure = fals }); } } + } else { + headers = await checkForPostData(socket, headers, data, data_hex); } - headers = await checkForPostData(socket, headers, data, data_hex); if (!headers.request_url) { // still no url, likely lost encryption stream, tell client to relog /* @@ -688,28 +698,13 @@ async function checkForPostData(socket, headers, data, data_hex) { // \n\n var header_length = data.length + 2; } + var post_data = CryptoJS.enc.Hex.parse(data_hex.substring(header_length * 2)); if (socket_sessions[socket.id].secure == true) { - var enc_data = CryptoJS.enc.Hex.parse(socket_sessions[socket.id].buffer.toString(CryptoJS.enc.Hex).substring(header_length * 2)); - if (enc_data.sigBytes > 0) { - if (headersAreStandard(enc_data.toString(CryptoJS.enc.Latin1))) { - // some builds (like our targeted 3833), send SECURE ON but then unencrypted headers - if (zdebug) console.log(" # Psuedo-encrypted POST Content (SECURE ON)", "on", socket.id); - // don't actually encrypt output - headers.psuedo_encryption = true; - ssid_sessions[socket.ssid].set("box-does-psuedo-encryption", true); - socket_sessions[socket.id].secure = false; - headers.post_data = await processRequest(socket, enc_data.toString(CryptoJS.enc.Hex), true); - } else { - // SECURE ON and detected encrypted data - ssid_sessions[socket.ssid].set("box-does-psuedo-encryption", false); - headers.post_data = CryptoJS.lib.WordArray.create(socket_sessions[socket.id].wtvsec.Decrypt(0, enc_data)) - if (zdebug) console.log(" # Encrypted POST Content (SECURE ON)", "on", socket.id); - } - } + if (zdebug) console.log(" # Encrypted POST Content (SECURE ON)", "on", socket.id, "[", post_data.sigBytes, "bytes ]"); } else { if (zdebug) console.log(" # Unencrypted POST Content", "on", socket.id); - headers.post_data = CryptoJS.enc.Hex.parse(socket_sessions[socket.id].buffer.toString(CryptoJS.enc.Hex).substring(header_length * 2)); } + headers.post_data = post_data; } } return headers; @@ -719,9 +714,20 @@ async function cleanupSocket(socket) { try { if (!zquiet) console.log(" * Destroying old WTVSec instance on disconnected socket", socket.id); delete socket_sessions[socket.id].buffer; - delete socket_sessions[socket.id].wtvsec; delete socket_sessions[socket.id]; + if (socket.ssid) { + if (ssid_sessions[socket.ssid].sockets.findIndex(element => element = socket.id) != -1) { + ssid_sessions[socket.ssid].sockets.splice(ssid_sessions[socket.ssid].sockets.findIndex(element => element = socket.id)); + } + var fuckyou = ssid_sessions[socket.ssid].sockets; + if (ssid_sessions[socket.ssid].sockets.length === 0 && ssid_sessions[socket.ssid].get("wtvsec_login")) { + // if last socket for SSID disconnected, destroy login session + if (!zquiet) console.log(" * Last socket from WebTV SSID", processSSID(socket.ssid),"disconnected, destroying initial WTVSec instance"); + ssid_sessions[socket.ssid].delete("wtvsec_login"); + } + } +; socket.end(); } catch (e) { console.log(" # Could not clean up socket data for socket ID", socket.id, e); @@ -736,7 +742,7 @@ async function handleSocket(socket) { socket_sessions[socket.id] = []; socket.setEncoding('hex'); //set data encoding (either 'ascii', 'utf8', or 'base64') socket.on('data', function (data_hex) { - socket.setTimeout(300); + socket.setTimeout(minisrv_config.config.socket_timeout); if (socket_sessions[socket.id].buffer) { socket_sessions[socket.id].buffer.concat(CryptoJS.enc.Hex.parse(data_hex)); } else { @@ -776,6 +782,17 @@ function integrateConfig(main, user) { return main; } +function returnAbsolsutePath(path) { + if (path.substring(0, 1) != "/" && path.substring(1, 1) != ":") { + // non-absolute path, so use current directory as base + path = (__dirname + "/" + path).replace(/\\/g, "/"); + } else { + // already absolute path + path = path.replace(/\\/g, "/"); + } + return path; +} + var z_title = "zefie's wtv minisrv v" + require('./package.json').version; console.log("**** Welcome to " + z_title + " ****"); console.log(" *** Reading global configuration..."); @@ -784,6 +801,8 @@ try { } catch (e) { throw ("ERROR: Could not read config.json", e); } +var service_vaults = new Array(); + try { if (fs.lstatSync(__dirname + "/user_config.json")) { console.log(" *** Reading user configuration..."); @@ -809,6 +828,12 @@ if (throw_me) { throw ("An error has occured while reading the configuration files."); } +if (minisrv_config.config.UserServiceVault) service_vaults.push({ "path": returnAbsolsutePath(minisrv_config.config.UserServiceVault), "name": "User Service Vault" }); +service_vaults.push({ "path": returnAbsolsutePath(minisrv_config.config.ServiceVault), "name": "Service Vault" }); +Object.keys(service_vaults).forEach(function (k) { + console.log(" * Using", service_vaults[k].name, "at", service_vaults[k].path); +}); + var service_ip = minisrv_config.config.service_ip; Object.keys(minisrv_config.services).forEach(function (k) { if (minisrv_config.services[k].disabled) return; diff --git a/zefie_wtvp_minisrv/config.json b/zefie_wtvp_minisrv/config.json index 448abd6d..f1153a89 100644 --- a/zefie_wtvp_minisrv/config.json +++ b/zefie_wtvp_minisrv/config.json @@ -1,9 +1,12 @@ { "config": { "service_ip": "0.0.0.0", + "ServiceVault": "ServiceVault", + "UserServiceVault": "UserServiceVault", "service_name": "HackTV", "send_tellyscripts": false, "hide_ssid_in_logs": true, + "socket_timeout": 350, "verbosity": 2 }, "services": { diff --git a/zefie_wtvp_minisrv/package.json b/zefie_wtvp_minisrv/package.json index 2783de3b..8f20cbef 100644 --- a/zefie_wtvp_minisrv/package.json +++ b/zefie_wtvp_minisrv/package.json @@ -1,6 +1,6 @@ { "name": "zefie_wtvp_minisrv", - "version": "0.8.1", + "version": "0.9.0", "description": "WebTV Service (WTVP) Emulation Server", "main": "app.js", "homepage": "https://github.com/zefie/zefie_wtvp_minisrv", diff --git a/zefie_wtvp_minisrv/zefie_wtvp_minisrv.njsproj b/zefie_wtvp_minisrv/zefie_wtvp_minisrv.njsproj index 176f14cf..4469c7a9 100644 --- a/zefie_wtvp_minisrv/zefie_wtvp_minisrv.njsproj +++ b/zefie_wtvp_minisrv/zefie_wtvp_minisrv.njsproj @@ -183,14 +183,13 @@ Code - - - - + + Code + Code - + @@ -227,10 +226,6 @@ - - - - \ No newline at end of file