Skip to content

Commit

Permalink
Merge pull request #36 from lexor90/master
Browse files Browse the repository at this point in the history
Cross Compilation features
  • Loading branch information
pmq20 committed Aug 22, 2020
2 parents 7b1b3bc + 55af917 commit 293f6e6
Show file tree
Hide file tree
Showing 3 changed files with 91 additions and 2 deletions.
55 changes: 55 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -100,6 +100,8 @@ Then,
--msi Generates a .msi installer for Windows
--pkg Generates a .pkg installer for macOS
--debug Enable debug mode
-o, --dest-os=OS Destination operating system (enum: win mac solaris freebsd openbsd linux android aix)
-a, --dest-arch=ARCH Destination CPU architecture (enum: arm arm64 ia32 mips mipsel ppc ppc64 x32 x64 x86 s390 s390x)
--quiet Enable quiet mode
-v, --version Prints the version of nodec and exit
-V, --node-version Prints the version of the Node.js runtime and exit
Expand Down Expand Up @@ -147,6 +149,59 @@ Note: To compile to 32-bit windows OS compatible programs on a 64-bit machine, y
| [asar](https://github.com/electron/asar) | Asar keeps the code archive and the executable separate while Node.js Packer links all JavaScript source code together with the Node.js virtual machine and generates a single executable as the final product. Asar uses JSON to store files' information while Node.js Packer uses SquashFS. |
| [AppImage](http://appimage.org/) | AppImage supports only Linux with a kernel that supports SquashFS, while Node.js Packer supports all three platforms of Linux, macOS and Windows, meanwhile without any special feature requirements from the kernel. |

## Cross Compilation

`nodec` also support cross-compilation. Since node.js is built from sources you will need to setup properly a toolchain in order
to get valid compilers to produce binaries for the destination platform.

You can easily do this with by using [crosstool-ng](https://github.com/crosstool-ng/crosstool-ng) or any other tool you like.

Once you're done with the build of a valid toolchain (don't forget to enable c++ if you use crosstool-ng which by default excludes it)
you will be able to compile properly. Just set-up your environment so that it will know to use your cross-compile toolchain rather than
your system's default build tools.

An example (you may need to adjust values or specify additional variables):


export AR="x86_64-unknown-linux-gnu-ar"
export CC="x86_64-unknown-linux-gnu-gcc"
export CXX="x86_64-unknown-linux-gnu-g++"
export LINK="x86_64-unknown-linux-gnu-g++"
export CPP="x86_64-unknown-linux-gnu-gcc -E"
export LD="x86_64-unknown-linux-gnu-ld"
export AS="x86_64-unknown-linux-gnu-as"
export CCLD="ax86_64-unknown-linux-gnu-gcc ${TARGET_ARCH}"
export NM="x86_64-unknown-linux-gnu-nm"
export STRIP="x86_64-unknown-linux-gnu-strip"
export OBJCOPY="x86_64-unknown-linux-gnu-objcopy"
export RANLIB="x86_64-unknown-linux-gnu-ranlib"
export F77="x86_64-unknown-linux-gnu-g77 ${TARGET_ARCH}"
unset LIBC

#Define flags
#export CXXFLAGS="-march=armv7-a"
export LDFLAGS="-L${CSTOOLS_LIB} -Wl,-rpath-link,${CSTOOLS_LIB} -Wl,-O1 -Wl,--hash-style=gnu"
export CFLAGS="-isystem${CSTOOLS_INC} -fexpensive-optimizations -frename-registers -fomit-frame-pointer -O2 -ggdb3"
export CPPFLAGS="-isystem${CSTOOLS_INC}"
# export CCFLAGS="-march=armv7-a"

#Tools
export CSTOOLS=/Volumes/crosstools/x86_64-unknown-linux-gnu
export CSTOOLS_INC=${CSTOOLS}/include
export CSTOOLS_LIB=${CSTOOLS}/lib
#export ARM_TARGET_LIB=$CSTOOLS_LIB
# export GYP_DEFINES="armv7=1"

#Define other things, those are not 'must' to have defined but we added
export SHELL="/bin/bash"
export TERM="screen"
export LANG="en_US.UTF-8"
export MAKE="make"

#Export the path for your system
#export HOME="/home/gioyik" #Change this one with the name of your user directory
export PATH=${CSTOOLS}/bin:/usr/arm-linux-gnueabi/bin/:$PATH

## To-do

- Eliminate dependending on an outside Node.js and npm when compiling
Expand Down
25 changes: 25 additions & 0 deletions bin/nodec
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,13 @@ $LOAD_PATH.unshift File.expand_path("../../lib", __FILE__)
require "compiler"
require 'optparse'

# took directly from https://github.com/nodejs/node/blob/master/configure#L47,L50
VALID_OS = ['win', 'mac', 'solaris', 'freebsd', 'openbsd', 'linux', 'android', 'aix']
VALID_CPU = [
'arm', 'arm64', 'ia32', 'mips', 'mipsel', 'ppc', 'ppc64', 'x32', 'x64', 'x86',
's390', 's390x'
]

USAGE = %Q{
Node.js Compiler (nodec) v#{::Compiler::VERSION}
Expand Down Expand Up @@ -124,6 +131,24 @@ OptionParser.new do |opts|
options[:debug] = true
end

opts.on('-osOS', "--dest-os=OS", "Destination operating system (enum: #{VALID_OS.join(' ')})") do |os|
unless VALID_OS.include? os
puts "Invalid destination (got: --dest-os=#{os}), pick one of: #{VALID_OS.join(' ')}"
exit 1
end

options[:os] = os
end

opts.on('-archARCH', "--dest-arch=ARCH", "Destination CPU architecture (enum: #{VALID_CPU.join(' ')})") do |arch|
unless VALID_CPU.include? arch
puts "Invalid destination (got: --dest-arch=#{arch}), pick one of: #{VALID_CPU.join(' ')}"
exit 1
end

options[:arch] = arch
end

opts.on("--quiet", "Enable quiet mode") do
options[:quiet] = true
end
Expand Down
13 changes: 11 additions & 2 deletions lib/compiler.rb
Original file line number Diff line number Diff line change
Expand Up @@ -388,6 +388,9 @@ def make_enclose_io_vars

def compile_win
@utils.chdir(@tmpdir_node) do
# --without-intl=none fixes: icutrim.py - it tries to run a binary made for linux on mac
# --cross-compiling is required require host executables rather than target ones
# --without-snapshot avoids mksnapshot to run on host platform after build
@utils.run("call vcbuild.bat #{@options[:debug] ? 'debug' : ''} #{@options[:vcbuild_args]}")
end
src = File.join(@tmpdir_node, (@options[:debug] ? 'Debug\\node.exe' : 'Release\\node.exe'))
Expand All @@ -396,7 +399,10 @@ def compile_win

def compile_mac
@utils.chdir(@tmpdir_node) do
@utils.run("./configure #{@options[:debug] ? '--debug --xcode' : ''}")
# --without-intl=none fixes: icutrim.py - it tries to run a binary made for linux on mac
# --cross-compiling is required require host executables rather than target ones
# --without-snapshot avoids mksnapshot to run on host platform after build
@utils.run("./configure #{@options[:debug] ? '--debug --xcode' : ''} #{@options[:os] ? '--cross-compiling --without-snapshot --with-intl=none': ''} #{@options[:os] ? '--dest-os=' + @options[:os]: ''} #{@options[:arch] ? '--dest-cpu=' + @options[:arch]: ''}")
@utils.run("make #{@options[:make_args]}")
end
if @options[:pkg]
Expand All @@ -418,7 +424,10 @@ def compile_mac

def compile_linux
@utils.chdir(@tmpdir_node) do
@utils.run("./configure #{@options[:debug] ? '--debug' : ''}")
# --without-intl=none fixes: icutrim.py - it tries to run a binary made for linux on mac
# --cross-compiling is required require host executables rather than target ones
# --without-snapshot avoids mksnapshot to run on host platform after build
@utils.run("./configure #{@options[:debug] ? '--debug' : ''} #{@options[:os] ? '--cross-compiling --without-snapshot --with-intl=none': ''} #{@options[:os] ? '--dest-os=' + @options[:os]: ''} #{@options[:arch] ? '--dest-cpu=' + @options[:arch]: ''}")
@utils.run("make #{@options[:make_args]}")
end
src = File.join(@tmpdir_node, "out/#{@options[:debug] ? 'Debug' : 'Release'}/node")
Expand Down

0 comments on commit 293f6e6

Please sign in to comment.