1

HI, I upload my php testing script to online vps server just now. The script used to parse a big size XML file(about 4M, 7000Lines). But my IE explorer show the online error message below.

Fatal error: Allowed memory size of 16777216 bytes exhausted (tried to allocate 77 bytes) in /var/www/test/result/index.php on line 26

I am sure I already tested the php script on localhost successfully.

Is there any configuration need be enable/modify on my VPS? Such as php.ini or some setting for apache server? I just verified there are about 200M memory usage are avaliable for my VPS. How can I fix this?

......
function startElementHandler ($parser,$name,$attrib){
    global $usercount;
    global $userdata;
    global $state; // Line #26; 
    //Debug
    //print "name is: ".$name."\n";
    switch ($name) {
        case $name=="_ID" : {
        $userdata[$usercount]["first"] = $attrib["FIRST"];
        $userdata[$usercount]["last"] = $attrib["LAST"];
        $userdata[$usercount]["nick"] = $attrib["NICK"];
        $userdata[$usercount]["title"] = $attrib["TITLE"];
        break;
        }

        ......

        default : {$state=$name;break;}
    }
}
Nano HE
  • 9,109
  • 31
  • 97
  • 137
  • 2
    keep in mind that one day your XML may outgrow your available memory... – Axarydax May 05 '10 at 10:14
  • 1
    which library are you using for parsing the file? If it's a big file you might want to consider using XMLReader over any other library, because it does not have to load the entire document into memory first. – Gordon May 05 '10 at 10:20
  • @Gordon, I didn't use some library, I just found the tutorial 'codehelp.co.uk/php/xmlparse1.php' and practiced it with my XML file. And I would learn XMLReader later. Thanks. – Nano HE May 05 '10 at 11:18
  • 1
    The tutorial uses the XmlParser library. Try this approach instead: http://www.ibm.com/developerworks/library/x-pullparsingphp.html – Gordon May 05 '10 at 11:21

7 Answers7

3

Your PHP configuration is limiting PHP to only 16 megabytes of memory. You need to modify the memory_limit configuration directive in php.ini to increase it.

Look for the line in php.ini that looks like this:

memory_limit = 16M

...and change to to a large value (16M = 16 megabytes, you could increase it to something like 64M for 64 megabytes, et cetera). If you can't find any line like that, add it.

If you prefer to only increase it on a per-script basis, you can also use ini_set() to change the value for that script only.

Amber
  • 507,862
  • 82
  • 626
  • 550
  • I think it would be better to set it larger only for this file, but leave the lower value for default config. – o0'. May 05 '10 at 10:11
  • @Dav, I modified the value to 64M, and it works well. Later I would learn more PHP & XML knowledge and imporve my code. @All, Thank you. – Nano HE May 05 '10 at 11:23
2

You can also use memory_get_peak_usage() to find out which part of the program is eating your memory.

Vili
  • 1,599
  • 15
  • 40
2

Use a SAX parser instead of a DOM parser, and you won't run out of memory. DOM occupies 8-10 times the memory that the actual document stream does, whereas SAX has a reasonable constant overhead regardless of document size.

Adrian
  • 2,244
  • 18
  • 20
1
ini_set("memory_limit","XXM");

please notice that some servers prevent this from working (though in a VPS this shouldn't be an issue, it's mostly a web hosting problem).

edit: instead of "XX" write the actual size, such as 128M

o0'.
  • 11,739
  • 19
  • 60
  • 87
  • +1 If you can then use this just for the code that needs the extra memory rather than making it global. – Colonel Sponsz May 05 '10 at 10:16
  • @Lo'oris, I tried to inserted `ini_set("memory_limit","128M");` to my index.php file. But it still can't work. showed the same error message. I guess maybe my VPS can't support the function. I can only choice modify php.ini and reboot my web service :-(. Thank you. ` – Nano HE May 05 '10 at 10:38
1

Make sure that you have specified the correct acceptable settings for:

  • file_uploads
  • upload_max_filesize
  • max_input_time
  • memory_limit
  • max_execution_time
  • post_max_size

You can call the phpinfo() function to find the location of your php.ini file, it will also tell you the current values for the following settings that you need to modify.

You could use the ini_set function to set some of those values from within your script too.

SEE:

Howto optimize your PHP installation to handle large file uploads.

Sarfraz
  • 377,238
  • 77
  • 533
  • 578
1

It is dirty but in some cases with large XML files it is faster to get the values via regular expressions! And if it is a well formatted XML there should be no problem!

pseudo code:

preg_match('+<title>(.*)</title>+', $xml_content, $matches);
var_dump($matches);
powtac
  • 40,542
  • 28
  • 115
  • 170
0

for shared hosting put this line to you index.php

ini_set("memory_limit","128M");
Saurabh Chandra Patel
  • 12,712
  • 6
  • 88
  • 78