首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >PHP x86内存限制

PHP x86内存限制
EN

Stack Overflow用户
提问于 2019-03-07 16:04:11
回答 2查看 426关注 0票数 3

我有一个需要base64编码的文件,即418 MB,但是我一直收到内存限制错误。我已经在我的memory_limit=2048M中设置了php.ini,但仍然不能将它作为带有x86 CLI版本的base64字符串读入内存。

脚本

代码语言:javascript
复制
<?php

echo "\r\n";
echo "\r\nMemory Usage\r\n" . memory_get_usage(false) . " Bytes\r\nReal " . memory_get_usage(true) . " Bytes\r\n";
echo "\r\nPeak Memory Usage\r\n" . memory_get_peak_usage(false). " Bytes\r\nReal " . memory_get_peak_usage(true) . " Bytes\r\n";
echo "\r\nMemory Limit\r\n" . ini_get('memory_limit') . "\r\n";

$file = file_get_contents('C:\Path\To\File');

echo "\r\n";
echo "\r\nMemory Usage\r\n" . memory_get_usage(false) . " Bytes\r\nReal " . memory_get_usage(true) . " Bytes\r\n";
echo "\r\nPeak Memory Usage\r\n" . memory_get_peak_usage(false). " Bytes\r\nReal " . memory_get_peak_usage(true) . " Bytes\r\n";
echo "\r\nMemory Limit\r\n" . ini_get('memory_limit') . "\r\n";

$encodedFile = base64_encode($file);

echo "\r\n";
echo "\r\nMemory Usage\r\n" . memory_get_usage(false) . " Bytes\r\nReal " . memory_get_usage(true) . " Bytes\r\n";
echo "\r\nPeak Memory Usage\r\n" . memory_get_peak_usage(false). " Bytes\r\nReal " . memory_get_peak_usage(true) . " Bytes\r\n";
echo "\r\nMemory Limit\r\n" . ini_get('memory_limit') . "\r\n";

?>

运行该脚本的生成以下.

代码语言:javascript
复制
PS C:\> php .\MemoryIssueTest.php


Memory Usage
382184 Bytes
Real 2097152 Bytes

Peak Memory Usage
422256 Bytes
Real 2097152 Bytes

Memory Limit
2048M


Memory Usage
447075680 Bytes
Real 448790528 Bytes

Peak Memory Usage
447084280 Bytes
Real 448790528 Bytes

Memory Limit
2048M

VirtualAlloc() failed: [0x00000008] Not enough memory resources are available to process this command.


VirtualAlloc() failed: [0x00000008] Not enough memory resources are available to process this command.

PHP Fatal error:  Out of memory (allocated 448790528) (tried to allocate 593015064 bytes) in C:\MemoryIssueTest.php on line 14
PHP Stack trace:
PHP   1. {main}() C:\MemoryIssueTest.php:0
PHP   2. base64_encode() C:\MemoryIssueTest.php:14

Fatal error: Out of memory (allocated 448790528) (tried to allocate 593015064 bytes) in C:\MemoryIssueTest.php on line 14

Call Stack:
    0.4046     382152   1. {main}() C:\MemoryIssueTest.php:0
   33.4669  447075680   2. base64_encode() C:\MemoryIssueTest.php:14

升级到PHP64位版本后,我从相同的脚本中获得以下结果.

代码语言:javascript
复制
PS C:\> php .\MemoryIssueTest.php


Memory Usage
402088 Bytes
Real 2097152 Bytes

Peak Memory Usage
444160 Bytes
Real 2097152 Bytes

Memory Limit
2048M


Memory Usage
440804144 Bytes
Real 442499072 Bytes

Peak Memory Usage
440812824 Bytes
Real 442499072 Bytes

Memory Limit
2048M


Memory Usage
1025909576 Bytes
Real 1027604480 Bytes

Peak Memory Usage
1025909760 Bytes
Real 1027604480 Bytes

Memory Limit
2048M

据我理解,x86应用程序应该能够消耗比1GB更多的内存。php的x86版本是否硬编码,只允许小于1GB?如果不是,为什么我只需要消耗1GB,但我有2GB限制时,就会得到PHP Fatal error: Out of memory错误?

EN

回答 2

Stack Overflow用户

回答已采纳

发布于 2019-03-07 17:26:30

理论上,您应该能够在Windows上使用x86进程分配高达2GB的内存。然而,对于您可以分配多少,还有其他的限制。关键是:可用地址空间中的内存碎片。由于base64_encode同时分配所需的内存,因此需要足够的连续地址空间来编码整个字符串。您更有可能有足够的64位地址空间,这就是为什么64位版本的PHP运行良好的原因。

有关此答案中的更多信息,请参见:Java maximum memory on Windows XP

增编:在我的测试中,我只能分配比你稍微多一点,但是更小的地址分配让我更接近2GB的限制。

增编2:如果您绝对需要使用32位版本,并且正在对文件进行编码,您可以在某种程度上通过以3字节的倍数编码来解决这个问题,然后您可以将它们连接起来。

代码语言:javascript
复制
// Example, from memory string to file.
$current_position = 0;
$length = strlen($file);
$outputfile = fopen('testoutput.txt', 'w');
while($current_position < $length) {
  fwrite($outputfile, base64_encode(substr($file, $current_position, 60000)));
  $current_position += 60000;
}
fclose($outputfile);

或者一路走来,从一个文件到另一个文件,这些文件分配的内存很少:

代码语言:javascript
复制
$inputfile = fopen('test.mp4', 'rb');
$outputfile = fopen('testoutput2.txt', 'w');
while( ($str = fread($inputfile, 61440)) !== false ) {
  if($str === '') {
    break;
  }
  fwrite($outputfile, base64_encode($str));
  $current_position += 61440;
}
fclose($outputfile);
票数 2
EN

Stack Overflow用户

发布于 2019-03-07 18:13:48

检查您是否有足够的内存。如果您只有<1gb的空闲系统内存(或其他虚拟内存限制,如容器内存限制),则更改限制和更改可寻址内存量(64位)并不重要。

票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/55048112

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档