TypePHP 编译器
https://swoole.com/aot/
You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
175 lines
6.3 KiB
175 lines
6.3 KiB
<?php
|
|
|
|
namespace TypePhpTest\Build;
|
|
|
|
use PHPUnit\Framework\TestCase;
|
|
use RuntimeException;
|
|
use TypePhp\Build\NativeDependencyAuditor;
|
|
|
|
final class NativeDependencyAuditorTest extends TestCase
|
|
{
|
|
public function testToolchainRuntimeLibrariesAreAllowedForWasip2(): void
|
|
{
|
|
(new NativeDependencyAuditor())->assertLinkFlags(
|
|
'wasip2',
|
|
['-fwasm-exceptions', '-lsetjmp', '-lunwind', '-Wl,--gc-sections'],
|
|
);
|
|
self::addToAssertionCount(1);
|
|
}
|
|
|
|
public function testExternalLibraryIsRejected(): void
|
|
{
|
|
$this->expectException(RuntimeException::class);
|
|
$this->expectExceptionMessage('must not link external library `-lcurl`');
|
|
(new NativeDependencyAuditor())->assertLinkFlags('native', ['-lcurl']);
|
|
}
|
|
|
|
public function testNativeForbiddenSymbolIsRejected(): void
|
|
{
|
|
$this->expectException(RuntimeException::class);
|
|
$this->expectExceptionMessage('mmap');
|
|
(new NativeDependencyAuditor())->assertUndefinedSymbols(
|
|
'native',
|
|
" U malloc@GLIBC_2.2.5\n U mmap@GLIBC_2.2.5\n",
|
|
);
|
|
}
|
|
|
|
/** @dataProvider forbiddenNativeCapabilityProvider */
|
|
public function testNativeCapabilityFamiliesAreRejected(string $symbol): void
|
|
{
|
|
$this->expectException(RuntimeException::class);
|
|
$this->expectExceptionMessage($symbol);
|
|
(new NativeDependencyAuditor())->assertUndefinedSymbols(
|
|
'native',
|
|
" U {$symbol}@GLIBC_2.2.5\n",
|
|
);
|
|
}
|
|
|
|
public static function forbiddenNativeCapabilityProvider(): array
|
|
{
|
|
return [
|
|
'process pipe' => ['pipe'],
|
|
'descriptor ioctl' => ['ioctl'],
|
|
'descriptor selection' => ['select'],
|
|
'network socket' => ['socket'],
|
|
'network connection' => ['connect'],
|
|
'system logging' => ['syslog'],
|
|
];
|
|
}
|
|
|
|
public function testWasip2FilesystemImportsAreAllowed(): void
|
|
{
|
|
(new NativeDependencyAuditor())->assertUndefinedSymbols(
|
|
'wasip2',
|
|
" U __imported_wasi_snapshot_preview1_fd_write\n"
|
|
. " U __imported_wasi_snapshot_preview1_fd_read\n"
|
|
. " U __imported_wasi_snapshot_preview1_path_open\n",
|
|
);
|
|
self::addToAssertionCount(1);
|
|
}
|
|
|
|
public function testNativeFilesystemSymbolsAreAllowed(): void
|
|
{
|
|
(new NativeDependencyAuditor())->assertUndefinedSymbols(
|
|
'native',
|
|
" U fopen@GLIBC_2.2.5\n"
|
|
. " U stat@GLIBC_2.2.5\n"
|
|
. " U read@GLIBC_2.2.5\n",
|
|
);
|
|
self::addToAssertionCount(1);
|
|
}
|
|
|
|
public function testAndroidAllowsRequiredBionicAbiButStillRejectsNetwork(): void
|
|
{
|
|
$auditor = new NativeDependencyAuditor();
|
|
$auditor->assertUndefinedSymbols(
|
|
'android',
|
|
" U closelog\n"
|
|
. " U openlog\n"
|
|
. " U syscall\n"
|
|
. " U syslog\n",
|
|
);
|
|
self::addToAssertionCount(1);
|
|
|
|
$this->expectException(RuntimeException::class);
|
|
$this->expectExceptionMessage('socket');
|
|
$auditor->assertUndefinedSymbols('android', " U socket\n");
|
|
}
|
|
|
|
public function testOnlyNonPosixExceptionsNeedAnAllowlistEntry(): void
|
|
{
|
|
self::assertContains('flock', NativeDependencyAuditor::NON_POSIX_HOST_FUNCTION_ALLOWLIST);
|
|
foreach (['fopen', 'strdup', 'dup', 'dup2', 'mkstemp', 'chown', 'getuid'] as $standardName) {
|
|
self::assertNotContains(
|
|
$standardName,
|
|
NativeDependencyAuditor::NON_POSIX_HOST_FUNCTION_ALLOWLIST,
|
|
);
|
|
}
|
|
self::assertNotContains('socket', NativeDependencyAuditor::NON_POSIX_HOST_FUNCTION_ALLOWLIST);
|
|
}
|
|
|
|
public function testConsoleOutputImportsAreAllowed(): void
|
|
{
|
|
(new NativeDependencyAuditor())->assertUndefinedSymbols(
|
|
'wasip2',
|
|
" U __imported_wasi_snapshot_preview1_fd_write\n"
|
|
. " U __imported_wasi_snapshot_preview1_proc_exit\n",
|
|
);
|
|
self::addToAssertionCount(1);
|
|
}
|
|
|
|
public function testWasip2RejectsSocketAndProcessControlImports(): void
|
|
{
|
|
$this->expectException(RuntimeException::class);
|
|
$this->expectExceptionMessage('proc_raise');
|
|
(new NativeDependencyAuditor())->assertUndefinedSymbols(
|
|
'wasip2',
|
|
" U __imported_wasi_snapshot_preview1_fd_write\n"
|
|
. " U __imported_wasi_snapshot_preview1_sock_recv\n"
|
|
. " U __imported_wasi_snapshot_preview1_proc_raise\n",
|
|
);
|
|
}
|
|
|
|
public function testStandardLibraryClockSleepAndEntropyImportsAreAllowed(): void
|
|
{
|
|
$auditor = new NativeDependencyAuditor();
|
|
$auditor->assertUndefinedSymbols(
|
|
'native',
|
|
" U clock_gettime@GLIBC_2.17\n"
|
|
. " U nanosleep@GLIBC_2.2.5\n",
|
|
);
|
|
$auditor->assertUndefinedSymbols(
|
|
'wasip2',
|
|
" U __imported_wasi_snapshot_preview1_clock_time_get\n"
|
|
. " U __imported_wasi_snapshot_preview1_poll_oneoff\n"
|
|
. " U __imported_wasi_snapshot_preview1_random_get\n",
|
|
);
|
|
self::addToAssertionCount(1);
|
|
}
|
|
|
|
public function testWindowsSystemRuntimeImportsAreAllowed(): void
|
|
{
|
|
(new NativeDependencyAuditor())->assertWindowsImports(
|
|
" KERNEL32.dll\n VCRUNTIME140.dll\n ucrtbase.dll\n",
|
|
);
|
|
self::addToAssertionCount(1);
|
|
}
|
|
|
|
public function testWindowsPhpRuntimeDllIsRejected(): void
|
|
{
|
|
$this->expectException(RuntimeException::class);
|
|
$this->expectExceptionMessage('phpx.dll');
|
|
(new NativeDependencyAuditor())->assertWindowsImports(
|
|
" KERNEL32.dll\n phpx.dll\n",
|
|
);
|
|
}
|
|
|
|
public function testWindowsForbiddenCapabilityImportIsRejected(): void
|
|
{
|
|
$this->expectException(RuntimeException::class);
|
|
$this->expectExceptionMessage('socket');
|
|
(new NativeDependencyAuditor())->assertWindowsImports(
|
|
" WS2_32.dll\n 123 socket\n",
|
|
);
|
|
}
|
|
}
|
|
|