1 | 'use strict';
|
---|
2 |
|
---|
3 | var platform = require('os').platform();
|
---|
4 | var spawnSync = require('child_process').spawnSync;
|
---|
5 | var readdirSync = require('fs').readdirSync;
|
---|
6 |
|
---|
7 | var GLIBC = 'glibc';
|
---|
8 | var MUSL = 'musl';
|
---|
9 |
|
---|
10 | var spawnOptions = {
|
---|
11 | encoding: 'utf8',
|
---|
12 | env: process.env
|
---|
13 | };
|
---|
14 |
|
---|
15 | if (!spawnSync) {
|
---|
16 | spawnSync = function () {
|
---|
17 | return { status: 126, stdout: '', stderr: '' };
|
---|
18 | };
|
---|
19 | }
|
---|
20 |
|
---|
21 | function contains (needle) {
|
---|
22 | return function (haystack) {
|
---|
23 | return haystack.indexOf(needle) !== -1;
|
---|
24 | };
|
---|
25 | }
|
---|
26 |
|
---|
27 | function versionFromMuslLdd (out) {
|
---|
28 | return out.split(/[\r\n]+/)[1].trim().split(/\s/)[1];
|
---|
29 | }
|
---|
30 |
|
---|
31 | function safeReaddirSync (path) {
|
---|
32 | try {
|
---|
33 | return readdirSync(path);
|
---|
34 | } catch (e) {}
|
---|
35 | return [];
|
---|
36 | }
|
---|
37 |
|
---|
38 | var family = '';
|
---|
39 | var version = '';
|
---|
40 | var method = '';
|
---|
41 |
|
---|
42 | if (platform === 'linux') {
|
---|
43 | // Try getconf
|
---|
44 | var glibc = spawnSync('getconf', ['GNU_LIBC_VERSION'], spawnOptions);
|
---|
45 | if (glibc.status === 0) {
|
---|
46 | family = GLIBC;
|
---|
47 | version = glibc.stdout.trim().split(' ')[1];
|
---|
48 | method = 'getconf';
|
---|
49 | } else {
|
---|
50 | // Try ldd
|
---|
51 | var ldd = spawnSync('ldd', ['--version'], spawnOptions);
|
---|
52 | if (ldd.status === 0 && ldd.stdout.indexOf(MUSL) !== -1) {
|
---|
53 | family = MUSL;
|
---|
54 | version = versionFromMuslLdd(ldd.stdout);
|
---|
55 | method = 'ldd';
|
---|
56 | } else if (ldd.status === 1 && ldd.stderr.indexOf(MUSL) !== -1) {
|
---|
57 | family = MUSL;
|
---|
58 | version = versionFromMuslLdd(ldd.stderr);
|
---|
59 | method = 'ldd';
|
---|
60 | } else {
|
---|
61 | // Try filesystem (family only)
|
---|
62 | var lib = safeReaddirSync('/lib');
|
---|
63 | if (lib.some(contains('-linux-gnu'))) {
|
---|
64 | family = GLIBC;
|
---|
65 | method = 'filesystem';
|
---|
66 | } else if (lib.some(contains('libc.musl-'))) {
|
---|
67 | family = MUSL;
|
---|
68 | method = 'filesystem';
|
---|
69 | } else if (lib.some(contains('ld-musl-'))) {
|
---|
70 | family = MUSL;
|
---|
71 | method = 'filesystem';
|
---|
72 | } else {
|
---|
73 | var usrSbin = safeReaddirSync('/usr/sbin');
|
---|
74 | if (usrSbin.some(contains('glibc'))) {
|
---|
75 | family = GLIBC;
|
---|
76 | method = 'filesystem';
|
---|
77 | }
|
---|
78 | }
|
---|
79 | }
|
---|
80 | }
|
---|
81 | }
|
---|
82 |
|
---|
83 | var isNonGlibcLinux = (family !== '' && family !== GLIBC);
|
---|
84 |
|
---|
85 | module.exports = {
|
---|
86 | GLIBC: GLIBC,
|
---|
87 | MUSL: MUSL,
|
---|
88 | family: family,
|
---|
89 | version: version,
|
---|
90 | method: method,
|
---|
91 | isNonGlibcLinux: isNonGlibcLinux
|
---|
92 | };
|
---|