main funcions fixes
This commit is contained in:
26
desktop-operator/node_modules/read-binary-file-arch/README.md
generated
vendored
Normal file
26
desktop-operator/node_modules/read-binary-file-arch/README.md
generated
vendored
Normal file
@@ -0,0 +1,26 @@
|
||||
# read-binary-file-arch
|
||||
|
||||
A node module that reads the [CPU architecture](https://nodejs.org/api/process.html#processarch) of a binary file.
|
||||
|
||||
npm install read-binary-file-arch
|
||||
|
||||
## Usage
|
||||
|
||||
Pass a file path to `readBinaryFileArch`.
|
||||
|
||||
> [!NOTE]
|
||||
> Windows only supports valid PE binary files.
|
||||
|
||||
```js
|
||||
var { readBinaryFileArch } = require('read-binary-file-arch');
|
||||
|
||||
readBinaryFileArch(filePath).then((arch) => {
|
||||
console.log('arch: ', arch);
|
||||
}).catch((error) => {
|
||||
console.error(error.message);
|
||||
});
|
||||
```
|
||||
|
||||
## License
|
||||
|
||||
MIT
|
||||
20
desktop-operator/node_modules/read-binary-file-arch/cli.js
generated
vendored
Executable file
20
desktop-operator/node_modules/read-binary-file-arch/cli.js
generated
vendored
Executable file
@@ -0,0 +1,20 @@
|
||||
#!/usr/bin/env node
|
||||
const { readBinaryFileArch } = require('.');
|
||||
|
||||
async function main() {
|
||||
const args = process.argv.slice(2);
|
||||
if (args.length !== 1) {
|
||||
console.log('Usage: read-binary-file-arch <path-to-file>');
|
||||
process.exit(1);
|
||||
}
|
||||
const filePath = args[0];
|
||||
|
||||
try {
|
||||
const arch = await readBinaryFileArch(filePath);
|
||||
console.log(arch);
|
||||
} catch (error) {
|
||||
console.error(error.message);
|
||||
}
|
||||
}
|
||||
|
||||
main();
|
||||
12
desktop-operator/node_modules/read-binary-file-arch/index.d.ts
generated
vendored
Normal file
12
desktop-operator/node_modules/read-binary-file-arch/index.d.ts
generated
vendored
Normal file
@@ -0,0 +1,12 @@
|
||||
/**
|
||||
* Attempt to read the CPU architecture from a binary file.
|
||||
*
|
||||
* On Windows, only valid PE files are supported due to the 'file' command not
|
||||
* existing.
|
||||
* On Mac/Linux, all files are supported via the 'file' command.
|
||||
*
|
||||
* @param filePath
|
||||
*/
|
||||
export function readBinaryFileArch(
|
||||
filePath: string
|
||||
): Promise<NodeJS.Process['arch'] | null>;
|
||||
127
desktop-operator/node_modules/read-binary-file-arch/index.js
generated
vendored
Normal file
127
desktop-operator/node_modules/read-binary-file-arch/index.js
generated
vendored
Normal file
@@ -0,0 +1,127 @@
|
||||
const { promisify } = require('util');
|
||||
const { exec } = require('child_process');
|
||||
const { promises: fs } = require('fs');
|
||||
const execAsync = promisify(exec);
|
||||
|
||||
const debug = require('debug')('read-binary-file-arch');
|
||||
|
||||
// https://nodejs.org/api/process.html#processarch
|
||||
const SUPPORTED_ARCH = [
|
||||
'arm',
|
||||
'arm64',
|
||||
'ia32',
|
||||
'loong64',
|
||||
'mips',
|
||||
'mipsel',
|
||||
'ppc',
|
||||
'ppc64',
|
||||
'riscv64',
|
||||
's390',
|
||||
's390x',
|
||||
'x64',
|
||||
];
|
||||
|
||||
async function readPEArch(filePath) {
|
||||
const DOS_HEADER_PE_OFFSET = 0x3c;
|
||||
const COFF_HEADER_MACHINE_OFFSET = 4; // Offset after 'PE\0\0'
|
||||
const BUFFER_SIZE = 1024; // Enough to cover DOS header, PE header, and COFF header
|
||||
|
||||
const buffer = Buffer.alloc(BUFFER_SIZE);
|
||||
const fileHandle = await fs.open(filePath, 'r');
|
||||
|
||||
await fileHandle.read(buffer, 0, BUFFER_SIZE, 0);
|
||||
|
||||
// Find the PE header offset from the DOS header
|
||||
const peOffset = buffer.readUInt32LE(DOS_HEADER_PE_OFFSET);
|
||||
|
||||
// Read the machine type from the COFF header
|
||||
let machineType;
|
||||
try {
|
||||
machineType = buffer.readUInt16LE(
|
||||
peOffset + COFF_HEADER_MACHINE_OFFSET
|
||||
);
|
||||
} catch (error) {
|
||||
debug('read error:', error.message);
|
||||
throw new Error('Invalid PE file');
|
||||
}
|
||||
|
||||
// Mapping of machine types to architectures
|
||||
const MACHINE_TYPES = {
|
||||
0x014c: 'ia32',
|
||||
0x8664: 'x64',
|
||||
0x01c0: 'arm',
|
||||
0x01c4: 'arm', // ARMv7 Thumb-2 LE
|
||||
0xaa64: 'arm64',
|
||||
};
|
||||
|
||||
const arch = MACHINE_TYPES[machineType];
|
||||
debug('win32 arch:', arch);
|
||||
|
||||
await fileHandle.close();
|
||||
|
||||
return arch;
|
||||
}
|
||||
|
||||
async function getArchUsingFileCommand(filePath) {
|
||||
const { stdout } = await execAsync(`file "${filePath}"`);
|
||||
const output = stdout.trim();
|
||||
debug('file command output:', output);
|
||||
|
||||
const resultStart = filePath.length + 1; // skip 'filename:'
|
||||
const result = output.substring(resultStart).trim();
|
||||
debug('result:', result);
|
||||
|
||||
// 'file' architectures => Node architectures
|
||||
const FILE_ARCH = {
|
||||
x64: 'x64',
|
||||
'x86-64': 'x64',
|
||||
x86_64: 'x64',
|
||||
x86: 'ia32',
|
||||
i386: 'ia32',
|
||||
arm64: 'arm64',
|
||||
arm: 'arm',
|
||||
aarch64: 'arm64',
|
||||
ARMv7: 'arm',
|
||||
ppc_7400: 'ppc',
|
||||
// PE32 executable (console) Intel 80386, for MS Windows
|
||||
'Intel 80386': 'ia32',
|
||||
// ELF 64-bit LSB executable, IA-64, version 1 (SYSV), dynamically linked, interpreter /lib/ld-linux-ia64.so.2, for GNU/Linux 2.6.16
|
||||
'IA-64': 'x64',
|
||||
// ELF 32-bit MSB executable, PowerPC or cisco 4500, version 1 (SYSV), dynamically linked, interpreter /lib/ld.so.1, for GNU/Linux 2.6.32
|
||||
PowerPC: 'ppc',
|
||||
// ELF 32-bit MSB executable, MIPS, MIPS-IV version 1 (SYSV), dynamically linked, interpreter /lib/ld.so.1, for GNU/Linux 2.4.1
|
||||
MIPS: 'mips',
|
||||
};
|
||||
|
||||
const fileArchRegexStr = Object.keys(FILE_ARCH)
|
||||
.map((arch) => `(?:${arch})`)
|
||||
.join('|');
|
||||
const fileArchRegex = new RegExp(fileArchRegexStr);
|
||||
const fileArchMatch = result.match(fileArchRegex);
|
||||
debug('archMatch:', fileArchMatch && fileArchMatch[0]);
|
||||
const fileArch = fileArchMatch ? fileArchMatch[0] : null;
|
||||
const arch = FILE_ARCH[fileArch];
|
||||
|
||||
return arch;
|
||||
}
|
||||
|
||||
async function readBinaryFileArch(filePath) {
|
||||
const stat = await fs.stat(filePath);
|
||||
if (!stat.isFile()) {
|
||||
throw new Error(`${filePath} is not a file.`);
|
||||
}
|
||||
|
||||
let arch;
|
||||
|
||||
if (process.platform === 'win32') {
|
||||
// Windows only supports reading the architecture of valid PE files since
|
||||
// 'file' is not available.
|
||||
arch = await readPEArch(filePath);
|
||||
} else {
|
||||
arch = await getArchUsingFileCommand(filePath);
|
||||
}
|
||||
|
||||
return SUPPORTED_ARCH.includes(arch) ? arch : null;
|
||||
}
|
||||
|
||||
module.exports = { readBinaryFileArch };
|
||||
41
desktop-operator/node_modules/read-binary-file-arch/package.json
generated
vendored
Normal file
41
desktop-operator/node_modules/read-binary-file-arch/package.json
generated
vendored
Normal file
@@ -0,0 +1,41 @@
|
||||
{
|
||||
"name": "read-binary-file-arch",
|
||||
"version": "1.0.6",
|
||||
"description": "Reads a binary file to determine its CPU architecture.",
|
||||
"main": "index.js",
|
||||
"types": "./index.d.ts",
|
||||
"bin": {
|
||||
"read-binary-file-arch": "cli.js"
|
||||
},
|
||||
"scripts": {
|
||||
"test": "node test.js"
|
||||
},
|
||||
"repository": {
|
||||
"type": "git",
|
||||
"url": "git+ssh://git@github.com/samuelmaddock/read-binary-file-arch.git"
|
||||
},
|
||||
"keywords": [
|
||||
"binary",
|
||||
"file",
|
||||
"arch",
|
||||
"process"
|
||||
],
|
||||
"author": "Samuel Maddock",
|
||||
"license": "MIT",
|
||||
"bugs": {
|
||||
"url": "https://github.com/samuelmaddock/read-binary-file-arch/issues"
|
||||
},
|
||||
"homepage": "https://github.com/samuelmaddock/read-binary-file-arch#readme",
|
||||
"dependencies": {
|
||||
"debug": "^4.3.4"
|
||||
},
|
||||
"devDependencies": {
|
||||
"degit": "^2.8.4"
|
||||
},
|
||||
"prettier": {
|
||||
"trailingComma": "es5",
|
||||
"tabWidth": 2,
|
||||
"semi": true,
|
||||
"singleQuote": true
|
||||
}
|
||||
}
|
||||
36
desktop-operator/node_modules/read-binary-file-arch/test.js
generated
vendored
Normal file
36
desktop-operator/node_modules/read-binary-file-arch/test.js
generated
vendored
Normal file
@@ -0,0 +1,36 @@
|
||||
const { promises: fs } = require('fs');
|
||||
const path = require('path');
|
||||
const degit = require('degit');
|
||||
const { readBinaryFileArch } = require('.');
|
||||
|
||||
const samplesFolder = path.join(__dirname, 'samples');
|
||||
|
||||
async function before() {
|
||||
const emitter = degit('https://github.com/JonathanSalwan/binary-samples');
|
||||
emitter.on('info', console.debug);
|
||||
try {
|
||||
await emitter.clone(samplesFolder);
|
||||
} catch (error) {
|
||||
if (error.code !== 'DEST_NOT_EMPTY') {
|
||||
throw error;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
async function test() {
|
||||
await before();
|
||||
|
||||
const files = await fs.readdir(samplesFolder);
|
||||
for (const file of files) {
|
||||
const filePath = path.join(samplesFolder, file);
|
||||
|
||||
try {
|
||||
const arch = await readBinaryFileArch(filePath);
|
||||
console.log(`${arch}\t${file}`);
|
||||
} catch (error) {
|
||||
console.error(`${file}: ${error.message}`);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
test();
|
||||
Reference in New Issue
Block a user