From d2389de4f9e00a00d4471b00d9531c8f18483271 Mon Sep 17 00:00:00 2001 From: throwaway96 <68320646+throwaway96@users.noreply.github.com> Date: Sun, 30 Jul 2023 06:50:30 -0400 Subject: [PATCH 1/3] allow node.js services to be debugged The -d flag to run-js-service enables debugging, but it only works when /var/luna/preferences/devmode_enabled is a file. This patches out that check, allowing debugging of any non-system service run with this wrapper even when devmode_enabled is a directory. --- services/run-js-service | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/services/run-js-service b/services/run-js-service index 8b99578..bf9e84b 100755 --- a/services/run-js-service +++ b/services/run-js-service @@ -1,4 +1,6 @@ -#! /bin/sh +#!/bin/sh # :^) -eval "$(cat /usr/bin/run-js-service | sed 's/^thirdparty_jail=.*/thirdparty_jail=off/')" +eval "$(sed -e '/^thirdparty_jail=/s/=.*/=off/' \ + -e '\@/var/luna/preferences/devmode_enabled@s/if /&false \&\& /' \ + '/usr/bin/run-js-service')" From d22d827abb7178f65769b684c072f89087ac845c Mon Sep 17 00:00:00 2001 From: throwaway96 <68320646+throwaway96@users.noreply.github.com> Date: Fri, 24 Mar 2023 16:18:03 -0400 Subject: [PATCH 2/3] fix updateStartupScript in node v0.12.x Buffer.indexOf() doesn't exist in old Node.js, so read the file into a string instead. This fixes "TypeError: undefined is not a function" when calling updateStartupScript. Also return a stack trace in the Luna payload on error to aid in debugging any future issues. --- services/adapter.ts | 2 +- services/service.ts | 9 +++++++-- 2 files changed, 8 insertions(+), 3 deletions(-) diff --git a/services/adapter.ts b/services/adapter.ts index 607f260..10d9bd9 100644 --- a/services/adapter.ts +++ b/services/adapter.ts @@ -34,7 +34,7 @@ export const asyncExecFile: ( ) => Promise = Bluebird.Promise.promisify(execFile); export const asyncStat: (path: string) => Promise = Bluebird.Promise.promisify(fs.stat); export const asyncUnlink: (path: string) => Promise = Bluebird.Promise.promisify(fs.unlink); -export const asyncReadFile: (path: string, options?: any) => Promise = Bluebird.Promise.promisify(fs.readFile); +export const asyncReadFile: (path: string, options?: any) => Promise = Bluebird.Promise.promisify(fs.readFile); export const asyncWriteFile: (path: string, contents: string, options?: fs.WriteFileOptions) => Promise = Bluebird.Promise.promisify( fs.writeFile, ); diff --git a/services/service.ts b/services/service.ts index 1fac3f3..dae0b9d 100644 --- a/services/service.ts +++ b/services/service.ts @@ -527,10 +527,14 @@ function runService() { // RootMyTV v1 if (await isFile(startDevmode)) { const localChecksum = await hashFile(startDevmode, 'sha256'); + // Warn and return empty string on read error + let startDevmodeContents = await asyncReadFile(startDevmode, { encoding: 'utf-8'} ) + .catch((err) => (console.warn(`reading ${startDevmode} failed: ${err.toString()}`), '')) as string; + if (localChecksum !== bundledStartupChecksum && updatableChecksums.indexOf(localChecksum) !== -1) { await copyScript(bundledStartup, startDevmode); messages.push(`${startDevmode} updated!`); - } else if (localChecksum !== bundledJumpstartChecksum && (await asyncReadFile(startDevmode)).indexOf('org.webosbrew') !== -1) { + } else if (localChecksum !== bundledJumpstartChecksum && startDevmodeContents.indexOf('org.webosbrew') !== -1) { // Show notification about mismatched startup script if contains // org.webosbrew string (which is not used on jumpstart.sh nor // official start-devmode.sh) @@ -538,9 +542,10 @@ function runService() { } } } catch (err) { + console.log(`Startup script update failed: ${err.stack}`); messages = ['Startup script update failed!', ...messages, `Error: ${err.toString()}`]; await createToast(messages.join('
'), service); - return { returnValue: false, statusText: 'Startup script update failed.', messages }; + return { returnValue: false, statusText: 'Startup script update failed.', stack: err.stack, messages }; } if (messages.length) { From 54ad05950eedd81499406d0c03dc9069485704d9 Mon Sep 17 00:00:00 2001 From: throwaway96 <68320646+throwaway96@users.noreply.github.com> Date: Fri, 24 Mar 2023 16:36:55 -0400 Subject: [PATCH 3/3] only read start-devmode.sh once This file was being read twice: once to hash it, and again for its contents. The new function hashString() is now used to compute the hash from the data already read. --- services/service.ts | 18 +++++++++++++++--- 1 file changed, 15 insertions(+), 3 deletions(-) diff --git a/services/service.ts b/services/service.ts index dae0b9d..819f5cd 100644 --- a/services/service.ts +++ b/services/service.ts @@ -99,6 +99,15 @@ async function hashFile(filePath: string, algorithm: string): Promise { return hash.read(); } +/** + * Hashes a string with specified algorithm. + * + * Input should be UTF-8. + */ +function hashString(data: string, algorithm: string): string { + return createHash(algorithm).update(data, 'utf-8').digest('hex'); +} + /** * Elevates a package by name. */ @@ -526,10 +535,13 @@ function runService() { // RootMyTV v1 if (await isFile(startDevmode)) { - const localChecksum = await hashFile(startDevmode, 'sha256'); // Warn and return empty string on read error - let startDevmodeContents = await asyncReadFile(startDevmode, { encoding: 'utf-8'} ) - .catch((err) => (console.warn(`reading ${startDevmode} failed: ${err.toString()}`), '')) as string; + const startDevmodeContents = (await asyncReadFile(startDevmode, { encoding: 'utf-8' }).catch((err) => { + console.warn(`reading ${startDevmode} failed: ${err.toString()}`); + return ''; + })) as string; + + const localChecksum = hashString(startDevmodeContents, 'sha256'); if (localChecksum !== bundledStartupChecksum && updatableChecksums.indexOf(localChecksum) !== -1) { await copyScript(bundledStartup, startDevmode);