program story

치명적인 오류 : 134217728 바이트의 허용 메모리 크기가 소진되었습니다 (CodeIgniter + XML-RPC).

inputbox 2020. 10. 3. 10:37
반응형

치명적인 오류 : 134217728 바이트의 허용 메모리 크기가 소진되었습니다 (CodeIgniter + XML-RPC).


보고서 생성을 위해 데이터를 하나의 큰 데이터베이스에 저장하는 중앙 집중식 데이터베이스 하나에 새 판매 데이터를 주기적으로 보내는 클라이언트 POS (Point of Sale) 시스템이 많이 있습니다.

클라이언트 POS는 PHPPOS를 기반으로하며 표준 XML-RPC 라이브러리를 사용하여 서비스에 판매 데이터를 보내는 모듈을 구현했습니다. 서버 시스템은 CodeIgniter를 기반으로하며 웹 서비스 구성 요소에 XML-RPC 및 XML-RPCS 라이브러리를 사용합니다. 많은 판매 데이터를 보낼 때마다 (판매 테이블의 50 개 행 및 판매 내 각 항목과 관련된 sales_items의 개별 행) 다음 오류가 발생합니다.

Fatal error: Allowed memory size of 134217728 bytes exhausted (tried to allocate 54 bytes)

128M은에서 기본값 php.ini이지만 중단해야 할 엄청난 숫자라고 가정합니다. 실제로이 값을 1024M으로 설정하려고 시도했지만 오류가 발생하는 데 시간이 더 오래 걸립니다.

내가 취한 단계에 관해서는 서버 측에서 모든 처리를 비활성화하려고 시도했으며 입력에 관계없이 미리 준비된 응답을 반환하도록 조작했습니다. 그러나 문제는 실제 데이터 전송에 있다고 생각합니다. PHP의 최대 스크립트 실행 시간을 비활성화하려고 시도했지만 여전히 오류가 발생합니다.


memory_limitby 변경은 적절한 해결책 ini_set('memory_limit', '-1');아닙니다 . 그러지 마세요.

PHP 코드는 어딘가에 메모리 누수가있을 수 있으며 서버가 원하는 모든 메모리를 사용하도록 지시합니다. 문제를 전혀 해결하지 못했을 것입니다. 서버를 모니터링하면 현재 대부분의 RAM을 사용하고 디스크로 스와핑하는 것을 볼 수 있습니다.

코드에서 문제가되는 코드를 추적하고 수정해야합니다.


ini_set('memory_limit', '-1');기본 PHP 메모리 제한을 무시합니다 .


올바른 방법은 php.ini파일 을 편집하는 것 입니다. memory_limit원하는 값으로 편집 하십시오.

귀하의 질문에서와 같이 128M(기본 제한)이 초과되었으므로 그렇게 많이 걸리지 않아야하므로 코드에 심각한 문제가 있습니다.

왜 그렇게 많이 걸리는지 알고 있고 설정 memory_limit = 512M이상 을 허용하고 싶다면 좋을 것입니다.


PHP의 메모리 할당은 영구적으로 또는 일시적으로 조정할 수 있습니다.

영구적으로

두 가지 방법으로 PHP 메모리 할당을 영구적으로 변경할 수 있습니다.

php.ini파일에 대한 액세스 권한이있는 경우 memory_limit원하는 값에 대한 값을 편집 할 수 있습니다 .

php.ini파일에 대한 액세스 권한이없고 웹 호스트에서 허용하는 경우 .htaccess파일을 통해 메모리 할당을 재정의 할 수 있습니다 . 추가 php_value memory_limit 128M(또는 원하는 할당).

일시적인

PHP 파일 내에서 즉석에서 메모리 할당을 조정할 수 있습니다. 코드 ini_set('memory_limit', '128M');(또는 원하는 할당) 만 있으면됩니다. 값을 "-1"로 설정하여 메모리 제한을 제거 할 수 있습니다 (머신 또는 인스턴스 제한이 여전히 적용될 수 있음).


특히 ORM과 같은 추상화를 사용하는 경우 PHP 스크립트에서 메모리 누수가 발생하는 것은 매우 쉽습니다. Xdebug를 사용하여 스크립트를 프로파일 링하고 모든 메모리가 어디에 있는지 확인하십시오.


array_push를 사용하여 배열에 2,250 만 개의 레코드를 추가 할 때 4Gphp.ini 파일의 메모리 제한으로 사용하여 약 2 천만 개의 레코드에서 "메모리 고갈"치명적인 오류가 계속 발생했습니다 . 이 문제를 해결하기 위해

$old = ini_set('memory_limit', '8192M');

파일 상단에 있습니다. 이제 모든 것이 잘 작동합니다. PHP에 메모리 누수가 있는지 모르겠습니다. 그건 내 직업이 아니고 상관도 없습니다. 나는 내 일을 끝내기 만하면된다.

프로그램은 매우 간단합니다.

$fh = fopen($myfile);
while (!feof($fh)) {
    array_push($file, stripslashes(fgets($fh)));
}
fclose($fh);

치명적인 오류는 메모리 제한을 늘려 오류를 제거 할 때까지 3 행을 가리 킵니다.


난과 함께,이 오류가 발생 보관 memory_limit에 설정 php.ini하고, 값으로 올바르게 읽는 phpinfo().

이것을 변경함으로써 :

memory_limit=4G

이에:

memory_limit=4096M

이것은 PHP 7의 문제를 수정했습니다.


위의 오류가 표시되면-특히 (tried to allocate __ bytes)가 낮은 값인 경우 탈출구가없는 자체 호출 함수처럼 무한 루프의 표시 기일 수 있습니다.

function exhaustYourBytes()
{
    return exhaustYourBytes();
}

memory_limitfastcgi / fpm 을 변경하면이 문제를 제대로 해결할 수 있습니다 .

$vim /etc/php5/fpm/php.ini

128에서 512로 메모리 변경, 아래 참조

; Maximum amount of memory a script may consume (128 MB)
; http://php.net/memory-limit
memory_limit = 128M

...에

; Maximum amount of memory a script may consume (128 MB)
; http://php.net/memory-limit
memory_limit = 512M

이 두 줄을 활성화 한 후 작동하기 시작했습니다.

; Determines the size of the realpath cache to be used by PHP. This value should
; be increased on systems where PHP opens many files to reflect the quantity of
; the file operations performed.
; http://php.net/realpath-cache-size
realpath_cache_size = 16k

; Duration of time, in seconds for which to cache realpath information for a given
; file or directory. For systems with rarely changing files, consider increasing this
; value.
; http://php.net/realpath-cache-ttl
realpath_cache_ttl = 120


사이트의 루트 디렉토리 :

ini_set('memory_limit', '1024M');

Drupal 사용자의 경우이 Chris Lane의 답변 :

ini_set('memory_limit', '-1');

작동하지만 우리는 개봉 직후에 넣어야합니다

<?php

사이트의 루트 디렉토리에있는 index.php 파일의 태그.


Rather than changing the memory_limit value in your php.ini file, if there's a part of your code that could use a lot of memory, you could remove the memory_limit before that section runs, and then replace it after.

$limit = ini_get('memory_limit');
ini_set('memory_limit', -1);
// ... do heavy stuff
ini_set('memory_limit', $limit);

In Drupal 7, you can modify the memory limit in the settings.php file located in your sites/default folder. Around line 260, you'll see this:

ini_set('memory_limit', '128M');

Even if your php.ini settings are high enough, you won't be able to consume more than 128 MB if this isn't set in your Drupal settings.php file.


Change the memory limit in the php.ini file and restart Apache. After the restart, run the phpinfo(); function from any PHP file for a memory_limit change confirmation.

memory_limit = -1

Memory limit -1 means there is no memory limit set. It's now at the maximum.


PHP 5.3+ allows you to change the memory limit by placing a .user.ini file in the public_html folder. Simply create the above file and type the following line in it:

memory_limit = 64M

Some cPanel hosts only accept this method.


Crash page?

Enter image description here

(It happens when MySQL has to query large rows. By default, memory_limit is set to small, which was safer for the hardware.)

You can check your system existing memory status, before increasing php.ini:

# free -m
             total       used       free     shared    buffers     cached
Mem:         64457      63791        666          0       1118      18273
-/+ buffers/cache:      44398      20058
Swap:         1021          0       1021

Here I have increased it as in the following and then do service httpd restart to fix the crash page issue.

# grep memory_limit /etc/php.ini
memory_limit = 512M

For those who are scratching their heads to find out why on earth this little function should cause a memory leak, sometimes by a little mistake, a function starts recursively call itself for ever.

For example, a proxy class that has the same name for a function of the object that is going to proxy it.

class Proxy {

    private $actualObject;

    public function doSomething() {

        return $this->actualObjec->doSomething();
    }
}

Sometimes you may forget to bring that little actualObjec member and because the proxy actually has that doSomething method, PHP wouldn't give you any error and for a large class, it could be hidden from the eyes for a couple of minutes to find out why it is leaking the memory.


I had the error below while running on a dataset smaller than had worked previously.

Fatal error: Allowed memory size of 134217728 bytes exhausted (tried to allocate 4096 bytes) in C:\workspace\image_management.php on line 173

As the search for the fault brought me here, I thought I'd mention that it's not always the technical solutions in previous answers, but something more simple. In my case it was Firefox. Before I ran the program it was already using 1,157 MB.

It turns out that I'd been watching a 50 minute video a bit at a time over a period of days and that messed things up. It's the sort of fix that experts correct without even thinking about it, but for the likes of me it's worth bearing in mind.


Running the script like this (cron case for example): php5 /pathToScript/info.php produces the same error.

The correct way: php5 -cli /pathToScript/info.php


If you're running a WHM-powered VPS (virtual private server) you may find that you do not have permissions to edit PHP.INI directly; the system must do it. In the WHM host control panel, go to Service ConfigurationPHP Configuration Editor and modify memory_limit:

Updating memory_limit on WHM 11.48.4


I find it useful when including or requiring _dbconnection.php_ and _functions.php in files that are actually processed, rather than including in the header. Which is included in itself.

So if your header and footer is included, simply include all your functional files before the header is included.


This error is sometimes caused by a bug in the PHP code that causes recursions involving exception handling and possibly other operations. Unfortunately, I haven't been able to create a tiny example.

In these cases, which have happened for me several times, set_time_limit fails, and the browser keeps trying to load the PHP output, either with an infinite loop or with the fatal error message which is the topic of this question.

By reducing the allowed allocation size by adding

ini_set('memory_limit','1M');

near the beginning of your code you should be able to prevent the fatal error.

Then you may be left with a program that terminates, but is still difficult to debug.

At this point insert BreakLoop() calls inside your program to gain control and find out what loop or recursion in your program is causing the problem.

The definition of BreakLoop is as follows:

function BreakLoop($MaxRepetitions=500,$LoopSite="unspecified")
    {
    static $Sites=[];
    if (!@$Sites[$LoopSite] || !$MaxRepetitions)
        $Sites[$LoopSite]=['n'=>0, 'if'=>0];
    if (!$MaxRepetitions)
        return;
    if (++$Sites[$LoopSite]['n'] >= $MaxRepetitions)
        {
        $S=debug_backtrace(); // array_reverse
        $info=$S[0];
        $File=$info['file'];
        $Line=$info['line'];
        exit("*** Loop for site $LoopSite was interrupted after $MaxRepetitions repetitions. In file $File at line $Line.");
        }
    } // BreakLoop

The $LoopSite argument can be the name of a function in your code. It isn't really necessary, since the error message you will get will point you to the line containing the BreakLoop() call.


In my case it was a brief issue with the way a function was written. A memory leak can be caused by assigning a new value to a function's input variable, e.g.:

/**
* Memory leak function that illustrates unintentional bad code
* @param $variable - input function that will be assigned a new value
* @return null
**/
function doSomehting($variable){
    $variable = 'set value';
    // Or
    $variable .= 'set value';
}

Using yield might be a solution as well. See Generator syntax.

Instead of changing the PHP.ini file for a bigger memory storage, sometimes implementing a yield inside a loop might fix the issue. What yield does is instead of dumping all the data at once, it reads it one by one, saving a lot of memory usage.


Just add a ini_set('memory_limit', '-1'); line at the top of your web page.

And you can set your memory as per your need in the place of -1, to 16M, etc..


When I removed the following lines from my code, all worked OK!

set_include_path(get_include_path() . get_include_path() . '/phpseclib');
include_once('Net/SSH2.php');
include_once('Net/SFTP.php');

These lines were included in every file I was running. When running the files one by one, all worked OK, but when running all files together I got the memory leak issue. Somehow the "include_once" is not including things once, or I am doing something wrong...

참고URL : https://stackoverflow.com/questions/561066/fatal-error-allowed-memory-size-of-134217728-bytes-exhausted-codeigniter-xml

반응형