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

Use ffi-napi on browser #162

Open
kzaiwo opened this issue Jun 16, 2021 · 22 comments
Open

Use ffi-napi on browser #162

kzaiwo opened this issue Jun 16, 2021 · 22 comments

Comments

@kzaiwo
Copy link

kzaiwo commented Jun 16, 2021

I am trying to create a local browser-based application (no server, will not be hosted on a domain - usage is purely local).
I need to have access to some dlls so I need to use ffi-napi:

Example (what I need to use is not specifically the libm module, just simplifying the example):

    var ffi = require('ffi-napi')

    var libm = ffi.Library('libm', {
      'ceil': ['double', ['double']]
    })
    libm.ceil(1.5)

This works fine when on I am running on Electron. But when I compile it for use with the browser, I am getting this error message (which is being thrown by Webpack/node-gyp-build:

Error in mounted hook: "ReferenceError: require is not defined"

I understand that require is not native on the browser mode, but the framework I am using, I believe, already has browserify integrated (I am using Quasar framework). I think so because the other local modules I can use require() on the browser just fine.

Is there any way I can use ffi-napi on the browser?

Help!

@12Tall
Copy link

12Tall commented Jun 18, 2021

Hey buddy, I'm not sure how to require a native module in browser side, but I think you can call it by ipcMain/ipcRenderer in Electron Window. I also meet the error require is not defined with my electron app, not only for the native module. maybe the following link can help you a little bit:
electron/electron#9920 (comment)

@LoganDark
Copy link

Browsers run in an isolated context that cannot run native code, unless it's compiled to WebAssembly. But even then, the code cannot escape the webpage, for security reasons. The reason your Electron application can use node-ffi-napi is because it runs on unsandboxed Node, which can use native modules and interact with the system. But browser webpages cannot do that.

@Kali95739
Copy link

@LoganDark correction they can do that see npm had the browser based versions of all the node builtins modules that will run in the browser but for reasons that would be considered malicous they took those packages away just cause they took it away doesnt mean its not possible all we have to do is resolve the node builtins which is again possible experimental module loading etc

@LoganDark
Copy link

@LoganDark correction they can do that see npm had the browser based versions of all the node builtins modules that will run in the browser but for reasons that would be considered malicous they took those packages away just cause they took it away doesnt mean its not possible all we have to do is resolve the node builtins which is again possible experimental module loading etc

What you're saying makes no sense. In a normal web browser, like if you were to just start up Firefox or Chrome, there is no way for you to escape the sandbox. You can only execute sandboxed JavaScript and WebAssembly.

In Electron, the sandbox deliberately provides some escape hatches that trusted code can use to interact with the native system, such as requiring native Node modules. So it is possible to use ffi-napi on Electron. But still not in a normal browser.

@Kali95739
Copy link

Kali95739 commented Nov 5, 2022 via email

@Kali95739
Copy link

Kali95739 commented Nov 5, 2022 via email

@Kali95739
Copy link

Kali95739 commented Nov 5, 2022 via email

@LoganDark
Copy link

LoganDark commented Nov 5, 2022

You need to learn about module loading or module bundling g

I already know a fair bit about it, but what you're saying makes little to no sense.

Yes, you can run Linux in the browser, which can spawn subprocesses and run Node and whatever. Is this what you mean? Please note that these are not real subprocesses or native code, it is simply emulation.

@Kali95739
Copy link

Kali95739 commented Nov 5, 2022 via email

@Kali95739
Copy link

Here I will show

@Kali95739
Copy link

@Kali95739
Copy link

To avoid malicious use ^^ meaning it is possible to spawn the process in such a way that they wont release the orig package for the browser

@bluthen
Copy link

bluthen commented Nov 5, 2022

All of this doesn't mean what you think it does @Kali95739

child_process is a package that comes with node, but if it was also a npm package then someone might install a replacement thinking it was needed to be installed and if it was controlled by some random person then it is a good target to be malicious. It isn't that they are withholding packages to not run processes in a browser. They are holding that npm package name so someone doesn't make a malicious package and people install it with npm even though you do not need to install it (it comes with node).

There is javascript that runs in a browser. It is very locked down. You can NOT load up native libraries, you can NOT run system executable in it. It is locked down there is no full node environment. You can make packages that are limited that act like node modules, but it is not the same. These pretend or browser node modules only allow you to do what the browser lets you. They can be handy for compatibility between browser and node in some situations, but they are not full functioning like the original node module.

For example 'fs' replacement module for browsers often use a virtual file system, you can not access just any file on the computer like the real node version. Only a virtual file system for your web page. This can be handy to preload some files in this virtual file system then have some other module use that file to do processes. This other module then could work both in a browser or node, but it doesn't have full access to the computers file system in the browser, only a virtual files.

There may exist something like a limited child_process somewhere for browsers than can run js code in a webworker. But it won't run just any executable on that persons machine.

@Kali95739
Copy link

Kali95739 commented Nov 5, 2022 via email

@Kali95739
Copy link

Kali95739 commented Nov 5, 2022 via email

@Kali95739
Copy link

Almost there up until

@Kali95739
Copy link

no native build was found for platform=win32 arch=x64 runtime=node abi=undefinded uv= libc=glibc node=undefined

@Kali95739
Copy link

imported from /node_modules/@inigolabs/ref-napi

@bluthen
Copy link

bluthen commented Nov 6, 2022

You can't do it. It isn't just about making a umd bundle.

Just think if the browser let you run any native library. A website can just take over your whole computer. That's called a browser vulnerability. You can probably get $100k from google bug bounty or something. Anyway, this is the last comment I'll do, you are not listening.

@Kali95739
Copy link

I actually believe I may have been able to I replaced all of the modules in the browser including FS physical access thanks to promise its just that we need to bundle over es2015 because the modules are commonjs and es2015 mixed in so it related by bundling path must be a string atm if I can get past that and have the funcs yet in browser I will add another comment although placing browser based funcs I can still experiment module it in my node so maybe possible actually

@Kali95739
Copy link

Nvmd u are correct u cannot use this unless if u maybe somehow grepped the instance of the node installation seems to not work without the execPath func

@Kali95739
Copy link

No way to use it without a node install

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

5 participants