Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Node fails to start on MIPS32r2: "SyntaxError: Unexpected end of input" #3896

Closed
JohannesRudolph opened this issue Nov 18, 2015 · 30 comments
Closed
Labels
mips Issues and PRs related to the MIPS architecture.

Comments

@JohannesRudolph
Copy link

I cross compiled nodejs for a MIPS32r2 (BE) target (without FPU but FPU emulation in the kernel) using the OpenWRT Chaos Calmer toolchain. The target CPU is an AR9331 but I suppose that's irrelevant.

I compile using ./configure --without-snapshot --without-npm --dest-cpu=mips --dest-os=linux, so if I'm correct it should be compiled with hard float ABI.

When I run node on the target, I get the following error however.

root@host:/rim# nodejs test.js
undefined:1



SyntaxError: Unexpected end of input
    at Object.parse (native)
    at Function.startup.processConfig (node.js:263:27)
    at startup (node.js:33:13)
    at node.js:961:3

It's the same for 4.2.1 and 4.2.2. I'm not the only one getting this error, e.g. see http://techfindings.one/archives/2175

So to conclude this, nodejs is currently broken on MIPS. Any further info I can provide to you (since you're undoubtedly more qualified to fix this than I am)? How could I go about helping fix this?

If anyones interested in reproducing, here's the OpenWrt package I created for it.

include $(TOPDIR)/rules.mk

PKG_NAME:=node
PKG_VERSION:=v4.2.1
PKG_RELEASE:=1

PKG_SOURCE_PROTO:=git
PKG_SOURCE_URL:=https://github.com/nodejs/node.git
PKG_SOURCE_VERSION:=b7eff480d8fbeb0576bb98ca771fb1ad6f48e864
PKG_SOURCE_SUBDIR:=$(PKG_NAME)-$(PKG_VERSION)
PKG_SOURCE:=$(PKG_NAME)-$(PKG_VERSION)-$(PKG_SOURCE_VERSION).tar.gz


include $(INCLUDE_DIR)/package.mk

define Package/node
  DEPENDS:=+libstdcpp +libc +libpthread +librt +uclibcxx 
  SUBMENU:=Node.js
  SECTION:=lang
  CATEGORY:=Languages
  TITLE:=Node.js is a platform built on Chrome's JavaScript runtime
  URL:=http://nodejs.org/
endef

define Package/node/description
 Node.js is a platform built on Chrome's JavaScript runtime for easily building fast, scalable network applications. Node.js uses an event-driven, non-blocking I/O model that makes it lightweight and efficient, perfect for data-intensive real-time applications that run across distributed devices.
endef

define Build/Configure
    (cd $(PKG_BUILD_DIR); \
    CC="$(TOOLCHAIN_DIR)/bin/mips-openwrt-linux-gcc" \
    CXX="$(TOOLCHAIN_DIR)/bin/mips-openwrt-linux-g++" \
    AR="$(TOOLCHAIN_DIR)/bin/mips-openwrt-linux-ar" \
    RANLIB="$(TOOLCHAIN_DIR)/bin/mips-openwrt-linux-ranlib" \
    LD="$(TOOLCHAIN_DIR)/bin/mips-openwrt-linux-g++" \
    LINK="$(TOOLCHAIN_DIR)/bin/mips-openwrt-linux-g++" \
    PATH="/usr/bin/:$(PATH)" \
    LDFLAGS="-L$(TOOLCHAIN_DIR)/lib/ -Wl,-rpath-link $(TOOLCHAIN_DIR)/lib/" \
    ./configure --without-snapshot --without-npm --dest-cpu=mips --dest-os=linux \
    );
endef

define Build/Compile
    CC="$(TOOLCHAIN_DIR)/bin/mips-openwrt-linux-gcc" \
    CXX="$(TOOLCHAIN_DIR)/bin/mips-openwrt-linux-g++" \
    AR="$(TOOLCHAIN_DIR)/bin/mips-openwrt-linux-ar" \
    RANLIB="$(TOOLCHAIN_DIR)/bin/mips-openwrt-linux-ranlib" \
    LD="$(TOOLCHAIN_DIR)/bin/mips-openwrt-linux-g++" \
    LINK="$(TOOLCHAIN_DIR)/bin/mips-openwrt-linux-g++" \
    PATH="/usr/bin/:$(PATH)" \
    LDFLAGS="-L$(TOOLCHAIN_DIR)/lib/ -Wl,-rpath-link $(TOOLCHAIN_DIR)/lib/" \
    $(MAKE) $(PKG_JOBS) -C $(PKG_BUILD_DIR) DESTDIR="$(PKG_INSTALL_DIR)"
endef

define Package/node/install
    mkdir -p $(1)/usr/bin
    $(INSTALL_BIN) $(PKG_BUILD_DIR)/out/Release/node $(1)/usr/bin/nodejs
    $(INSTALL_BIN) ./files/node $(1)/usr/bin

    mkdir -p $(1)/usr/lib/node_modules
    $(CP) $(PKG_BUILD_DIR)/deps/npm $(1)/usr/lib/node_modules
    ln -sf /usr/lib/node_modules/npm/bin/npm-cli.js $(1)/usr/bin/npm
endef

$(eval $(call BuildPackage,node))
@bnoordhuis
Copy link
Member

There should be a config.gypi in the top-level directory, configure creates it. Can you post its contents?

@JohannesRudolph
Copy link
Author

# Do not edit. Generated by the configure script.
{ 'target_defaults': { 'cflags': [],
                       'default_configuration': 'Release',
                       'defines': [],
                       'include_dirs': [],
                       'libraries': []},
  'variables': { 'asan': 0,
                 'gas_version': '2.24',
                 'host_arch': 'mips',
                 'icu_small': 'false',
                 'mips_arch_variant': 'r2',
                 'mips_fpu_mode': 'fp32',
                 'node_byteorder': 'little',
                 'node_install_npm': 'false',
                 'node_prefix': '/usr/local',
                 'node_release_urlbase': '',
                 'node_shared_http_parser': 'false',
                 'node_shared_libuv': 'false',
                 'node_shared_openssl': 'false',
                 'node_shared_zlib': 'false',
                 'node_tag': '',
                 'node_use_dtrace': 'false',
                 'node_use_etw': 'false',
                 'node_use_lttng': 'false',
                 'node_use_openssl': 'true',
                 'node_use_perfctr': 'false',
                 'openssl_fips': '',
                 'openssl_no_asm': 0,
                 'python': '/usr/bin/python',
                 'target_arch': 'mips',
                 'uv_parent_path': '/deps/uv/',
                 'uv_use_dtrace': 'false',
                 'v8_can_use_fpu_instructions': 'true',
                 'v8_enable_gdbjit': 0,
                 'v8_enable_i18n_support': 0,
                 'v8_no_strict_aliasing': 1,
                 'v8_optimized_debug': 0,
                 'v8_random_seed': 0,
                 'v8_use_mips_abi_hardfloat': 'true',
                 'v8_use_snapshot': 0,
                 'want_separate_host_toolset': 0}}

I did also just try v5.1 - didn't compile at first because v8 apparently needs a patch:

diff --git a/deps/v8/src/log-utils.h b/deps/v8/src/log-utils.h
index 87dab52..5522829f1 100644
--- a/deps/v8/src/log-utils.h
+++ b/deps/v8/src/log-utils.h
@@ -5,6 +5,9 @@
 #ifndef V8_LOG_UTILS_H_
 #define V8_LOG_UTILS_H_

+#include <stdarg.h>
+#include <stdio.h>
+
 #include "src/allocation.h"
 #include "src/base/platform/mutex.h"
 #include "src/flags.h"

(or else I get compiler errors about missing va_list definition etc.)

But v5.1 fails with the same error on my OpenWRT board as v4.2.1 does (see first post).

@bnoordhuis
Copy link
Member

config.gypi looks alright to me. It gets baked into the binary and is then exposed as process.config here but the stack trace suggests something goes wrong parsing it. Maybe you can add a console.log to check what has actually been baked in?

@JohannesRudolph
Copy link
Author

Well, I did as you said and added two console.log statements in there. Unfortunately now console.log fails....

console.js:10
    throw new TypeError('Console expects a writable stream instance');
    ^

TypeError: Console expects a writable stream instance
    at new Console (console.js:10:11)
    at console.js:93:18
    at NativeModule.compile (node.js:969:5)
    at Function.NativeModule.require (node.js:917:18)
    at node.js:211:27
    at Function.startup.processConfig (node.js:269:5)
    at startup (node.js:35:13)
    at node.js:978:3

Something appears to be terribly broken with node on MIPS.

@bnoordhuis
Copy link
Member

Does substituting it with process._rawDebug() work?

@JohannesRudolph
Copy link
Author

I can try that.... recompiling takes > 30min though. Is there any way to get faster feedback (e.g. without recompiling node.js?)

@bnoordhuis
Copy link
Member

It should be an incremental build if you only touch src/node.js. Some files are regenerated but that's it.

@JohannesRudolph
Copy link
Author

It appears for some reason my openwrt build root always recompiles everything.... will report back with findings of using process._rawDebug. Is there any sensible reason console.log shouldn't work already during node.js startup? I have the feeling that v8 may actually be broken and execute bogus code...

@bnoordhuis
Copy link
Member

Is there any sensible reason console.log shouldn't work already during node.js startup?

node.js does some bootstrapping at startup. It's possible the process.config munging code runs too early for console.log to be working.

@targos
Copy link
Member

targos commented Nov 18, 2015

Just a question: is it expected to have 'node_byteorder': 'little' for a big-endian target CPU ?

@JohannesRudolph
Copy link
Author

@targos I can't comment on this but maybe @bnoordhuis can?

So here's the rebuild I've done with process._rawDebug()

diff --git a/src/node.js b/src/node.js
index 57a803c..3e54c64 100644
--- a/src/node.js
+++ b/src/node.js
@@ -266,6 +266,8 @@
     var config = NativeModule._source.config;
     delete NativeModule._source.config;

+    process._rawDebug('config pre-mod:\n' + config);
+
     // strip the gyp comment line at the beginning
     config = config.split('\n')
         .slice(1)
@@ -273,6 +275,8 @@
         .replace(/"/g, '\\"')
         .replace(/'/g, '"');

+  process._rawDebug('config post-mod:\n' + config);
+
     process.config = JSON.parse(config, function(key, value) {
       if (value === 'true') return true;
       if (value === 'false') return false;

Output:

root@rimbox-c49300003561:~# nodejs
config pre-mod:
# Do not edit. Generated by the configure script.
{ 'target_defaults': { 'cflags': [],
                       'default_configuration': 'Release',
                       'defines': [],
                       'include_dirs': [],
                       'libraries': []},
  'variables': { 'asan': 0,
                 'gas_version': '2.24',
                 'host_arch': 'mips',
                 'icu_small': 'false',
                 'mips_arch_variant': 'r2',
                 'mips_fpu_mode': 'fp32',
                 'node_byteorder': 'little',
                 'node_install_npm': 'false',
                 'node_prefix': '/usr/local',
                 'node_release_urlbase': '',
                 'node_shared_http_parser': 'false',
                 'node_shared_libuv': 'false',
                 'node_shared_openssl': 'false',
                 'node_shared_zlib': 'false',
                 'node_tag': '',
                 'node_use_dtrace': 'false',
                 'node_use_etw': 'false',
                 'node_use_lttng': 'false',
                 'node_use_openssl': 'true',
                 'node_use_perfctr': 'false',
                 'openssl_fips': '',
                 'openssl_no_asm': 0,
                 'python': '/usr/bin/python',
                 'target_arch': 'mips',
                 'uv_parent_path': '/deps/uv/',
                 'uv_use_dtrace': 'false',
                 'v8_can_use_fpu_instructions': 'true',
                 'v8_enable_gdbjit': 0,
                 'v8_enable_i18n_support': 0,
                 'v8_no_strict_aliasing': 1,
                 'v8_optimized_debug': 0,
                 'v8_random_seed': 0,
                 'v8_use_mips_abi_hardfloat': 'true',
                 'v8_use_snapshot': 0,
                 'want_separate_host_toolset': 0}}

config pre-mod:
# Do not edit. Generated by the configure script.
{ 'target_defaults': { 'cflags': [],
                       'default_configuration': 'Release',
                       'defines': [],
                       'include_dirs': [],
                       'libraries': []},
  'variables': { 'asan': 0,
                 'gas_version': '2.24',
                 'host_arch': 'mips',
                 'icu_small': 'false',
                 'mips_arch_variant': 'r2',
                 'mips_fpu_mode': 'fp32',
                 'node_byteorder': 'little',
                 'node_install_npm': 'false',
                 'node_prefix': '/usr/local',
                 'node_release_urlbase': '',
                 'node_shared_http_parser': 'false',
                 'node_shared_libuv': 'false',
                 'node_shared_openssl': 'false',
                 'node_shared_zlib': 'false',
                 'node_tag': '',
                 'node_use_dtrace': 'false',
                 'node_use_etw': 'false',
                 'node_use_lttng': 'false',
                 'node_use_openssl': 'true',
                 'node_use_perfctr': 'false',
                 'openssl_fips': '',
                 'openssl_no_asm': 0,
                 'python': '/usr/bin/python',
                 'target_arch': 'mips',
                 'uv_parent_path': '/deps/uv/',
                 'uv_use_dtrace': 'false',
                 'v8_can_use_fpu_instructions': 'true',
                 'v8_enable_gdbjit': 0,
                 'v8_enable_i18n_support': 0,
                 'v8_no_strict_aliasing': 1,
                 'v8_optimized_debug': 0,
                 'v8_random_seed': 0,
                 'v8_use_mips_abi_hardfloat': 'true',
                 'v8_use_snapshot': 0,
                 'want_separate_host_toolset': 0}}

config post-mod:

config post-mod:

undefined:1



SyntaxError: Unexpected end of input
    at Object.parse (native)
    at Function.startup.processConfig (node.js:284:27)
    at startup (node.js:35:13)
    at node.js:982:3
root@rimbox-c49300003561:~# 

So to me, it looks like the startup.processConfig is called twice, once with an empty (undefined?) input. Why that's the case I don't have a clue but looks like a bug to me.

@JohannesRudolph
Copy link
Author

Scrap what I've said in the last paragraph. It seems output is only repeated twice, there's actually only one call to startup.processConfig. So it seems the string manipulation in there is somehow to blame....

@bnoordhuis
Copy link
Member

is it expected to have 'node_byteorder': 'little' for a big-endian target CPU ?

node_byteorder is derived from python -c 'import sys; print sys.byteorder' so apparently this system (or at least its python binary) thinks it's little-endian.

@JohannesRudolph Are you cross-compiling?

@mscdex
Copy link
Contributor

mscdex commented Nov 18, 2015

Out of curiosity, what is the literal contents of test.js?

@mscdex mscdex added the mips Issues and PRs related to the MIPS architecture. label Nov 18, 2015
@JohannesRudolph
Copy link
Author

@bnoordhuis yes, I'm cross compiling from an x86_64 machine. Is there a way to override this byte order setting using a flag? In general using python from the host to get byte order would break all cross-compilation....

You'd have enough information from the ./configure --arch to set this anyway, so why involve python?

@JohannesRudolph
Copy link
Author

@mscdex It actually doesn't matter, I get the same errror running just 'nodejs' without args.

@JohannesRudolph
Copy link
Author

So I put the config from above directly into the code as a properly formatted object literal, and changed node_byteorder to big as well.

On to the next error:

root@rimbox-c49300003561:~# nodejs
buffer.js:607
  const buffer = this.subarray(start, end);
                      ^

RangeError: start offset of Uint8Array should be a multiple of 1
    at new Uint8Array (native)
    at Buffer.subarray (native)
    at Buffer.slice (buffer.js:607:23)
    at allocate (buffer.js:88:23)
    at new Buffer (buffer.js:49:12)
    at new exports.StringDecoder (string_decoder.js:47:21)
    at Object.emitKeypressEvents (readline.js:907:30)
    at REPLServer.Interface (readline.js:124:13)
    at new REPLServer (repl.js:313:13)
    at Object.exports.start (repl.js:487:14)

At this point I believe nodejs on MIPS is just not ready for prime time. Does the node core team even test on MIPS targets? All of these errors are fairly blocking...

@bnoordhuis
Copy link
Member

Does the node core team even test on MIPS targets?

There are no mips or mipsel machines in our CI matrix. The architecture is self-serve at the moment.

@JohannesRudolph
Copy link
Author

@bnoordhuis it shows....

Can't even run the simplest code :-(

root@rimbox-c49300003561:~# nodejs test.js 
nodejs: ../src/node_file.cc: 474: void node::InternalModuleReadFile(const v8::FunctionCallbackInfo<v8::Value>&): Assertion `(numchars) >= (0)' failed.
Aborted
root@rimbox-c49300003561:~# cat test.js 
console.log("hello world");
root@rimbox-c49300003561:~# 

@Fishrock123
Copy link
Contributor

cc @jbergstroem did you ever get anywhere with that tessel 2?

We should really aim to add those to the CI..

@jbergstroem
Copy link
Member

@Fishrock123 I have. It's up and running and I've been able to successfully build their firmware and upgrade it. The problem from our point of view is that running the test suite would take ages on it. My focus right now is to get better acquainted with their build system and look at what patches/build changes we can backport to make it easier for devs to integrate node on architectures like MIPS. I'm currently out of office, but I'll try to run a test run and see how long it'll actually take.

@darky
Copy link
Contributor

darky commented Feb 24, 2016

👍

@jasnell
Copy link
Member

jasnell commented Apr 4, 2016

Is this still relevant?

@JohannesRudolph
Copy link
Author

As far as I can see any underlying issues have not been fixed, so yes this
is still relevant.
Am 05.04.2016 00:12 schrieb "James M Snell" [email protected]:

Is this still relevant?


You are receiving this because you were mentioned.
Reply to this email directly or view it on GitHub
#3896 (comment)

@kapouer
Copy link
Contributor

kapouer commented May 1, 2016

@JohannesRudolph can your device run debian/sid ? if so you might give a shot at the nodejs package there since version 4.4.x builds and ci tests pass on mips/mipsel.
Version 6.0.0 fails on mipsel though (a v8 issue).

@wyze
Copy link

wyze commented May 5, 2016

@kapouer What failure are you getting with v6 and mipsel? And where do you see it being a v8 issue?

@kapouer
Copy link
Contributor

kapouer commented May 5, 2016

@wyze because of this build log. I reproduce on a different server with same CPU. I also tried some changes, like building without snapshot. When run with gdb, the stack trace is not useful, exactly as described here. Would a core dump be more useful in that case ?

@wyze
Copy link

wyze commented May 5, 2016

Thanks @kapouer. I was just curious as I am trying to build for OpenWRT and running into a build issue with v8 (undefined reference to 'nearbyintf' in src/assembler.cc) and was curious if it was the same issue.

@kapouer
Copy link
Contributor

kapouer commented May 5, 2016

@wyze You can see more build successful logs for mips, mips64el, etc... here. It's not official distribution, still it covers different architectures/os combinations.

@bnoordhuis
Copy link
Member

Closing, I'm reasonably sure this has been fixed now. (And if not - pull requests welcome!)

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
mips Issues and PRs related to the MIPS architecture.
Projects
None yet
Development

No branches or pull requests

10 participants