[PHP] Wyciek pamięci |
[PHP] Wyciek pamięci |
5.02.2018, 12:23:26
Post
#21
|
|
Grupa: Zarejestrowani Postów: 8 068 Pomógł: 1414 Dołączył: 26.10.2005 Ostrzeżenie: (0%) |
Jeśli używasz PHP7 to w teorii powinno Ci samo wywalić Exception. Próbowałeś to wywalić?
|
|
|
5.02.2018, 12:30:49
Post
#22
|
|
Grupa: Zarejestrowani Postów: 1 707 Pomógł: 266 Dołączył: 3.07.2012 Skąd: Poznań Ostrzeżenie: (0%) |
Wyrzuca stary,
|
|
|
5.02.2018, 18:14:06
Post
#23
|
|
Grupa: Zarejestrowani Postów: 3 033 Pomógł: 366 Dołączył: 24.05.2012 Ostrzeżenie: (0%) |
Ciężko jest odtworzyć Twój błąd nawet z zastosowaniem Twojego skryptu do obsługi wyjątków rzuca po prostu mi ten FAIL bez stack trace
|
|
|
5.02.2018, 22:28:49
Post
#24
|
|
Grupa: Zarejestrowani Postów: 1 240 Pomógł: 278 Dołączył: 11.03.2008 Ostrzeżenie: (0%) |
Kod ? ~ php7.1 test.php FAIL 2097152 FAIL 2097152 FAIL 2097152 FAIL 2097152 FAIL 2097152 FAIL 2097152 FAIL 2097152 FAIL 2097152 FAIL 2097152 FAIL 2097152 ? ~ php7.0 test.php FAIL 2097152 FAIL 2097152 FAIL 2097152 FAIL 2097152 FAIL 2097152 FAIL 2097152 FAIL 2097152 FAIL 2097152 7.2 nie mogę teraz zainstalować, także sprawdzę później. Ale już przy większej ilości interacji coś wzrasta: Kod FAIL 264 2097152 FAIL 265 2097152 FAIL 266 4194304 Ten post edytował markuz 5.02.2018, 22:51:21 -------------------- |
|
|
5.02.2018, 22:53:35
Post
#25
|
|
Grupa: Zarejestrowani Postów: 1 707 Pomógł: 266 Dołączył: 3.07.2012 Skąd: Poznań Ostrzeżenie: (0%) |
Pobawiłem się trochę Twoim i moim przykładem. Wniosek jest taki, że memory_get_usage(true) u mnie też pokazuje stałą wartość, ale już memory_get_usage() nie.
|
|
|
5.02.2018, 23:02:09
Post
#26
|
|
Grupa: Zarejestrowani Postów: 1 240 Pomógł: 278 Dołączył: 11.03.2008 Ostrzeżenie: (0%) |
Bez wyjątków nie pobiera więcej pamięci:
Kod 789 2097152
790 2097152 791 2097152 792 2097152 793 2097152 794 2097152 795 2097152 796 2097152 797 2097152 -------------------- |
|
|
5.02.2018, 23:07:50
Post
#27
|
|
Grupa: Zarejestrowani Postów: 1 707 Pomógł: 266 Dołączył: 3.07.2012 Skąd: Poznań Ostrzeżenie: (0%) |
I to też jest bardzo ciekawa obserwacja. Masz jakiś pomysł jak to ugryźć? Ten projekt to nie jest sprawa życia i śmierci, ale bardzo mnie ciekawi ten problem i wolałbym zachować wyjątki. Jak nic nie wymyślimy, to zapytam na Stack Overflow.
|
|
|
5.02.2018, 23:33:33
Post
#28
|
|
Grupa: Zarejestrowani Postów: 1 240 Pomógł: 278 Dołączył: 11.03.2008 Ostrzeżenie: (0%) |
Nie mam pomysłów. Wrzuć link do stackoverflow jak zadasz pytanie
-------------------- |
|
|
6.02.2018, 00:36:13
Post
#29
|
|
Grupa: Zarejestrowani Postów: 1 707 Pomógł: 266 Dołączył: 3.07.2012 Skąd: Poznań Ostrzeżenie: (0%) |
Temat już wisi. Nie będę linkował, ale podzielę się odpowiedzią jak tylko się pojawi.
|
|
|
6.02.2018, 19:15:58
Post
#30
|
|
Grupa: Zarejestrowani Postów: 3 033 Pomógł: 366 Dołączył: 24.05.2012 Ostrzeżenie: (0%) |
Kod FAIL
855 2097152 FAIL 856 2097152 FAIL 857 2097152 FAIL 858 2097152 FAIL 859 2097152 FAIL 860 2097152 FAIL 861 2097152 FAIL 862 2097152 FAIL 863 2097152 Ten post edytował com 6.02.2018, 19:16:23 |
|
|
6.02.2018, 19:23:01
Post
#31
|
|
Grupa: Zarejestrowani Postów: 1 707 Pomógł: 266 Dołączył: 3.07.2012 Skąd: Poznań Ostrzeżenie: (0%) |
@com zobacz, co pisaliśmy wyżej. Bez unset też będziesz miał stałą wartość.
|
|
|
6.02.2018, 19:30:52
Post
#32
|
|
Grupa: Zarejestrowani Postów: 3 033 Pomógł: 366 Dołączył: 24.05.2012 Ostrzeżenie: (0%) |
SmokAnalog ale unset jest na Exception, nie ma stałej wartości przy 220(u mnie/266 u kolegi markuz) mamy już 2*2097152, potem 4*2097152 itd. Problem polega na tym, że PHP trzyma referencje do wszystkich poprzednich Exception na stosie i trzeba je wykasować to pamieć nie rośnie zobacz doleciałem do pozycji 863
Ten post edytował com 6.02.2018, 19:36:37 |
|
|
6.02.2018, 19:39:51
Post
#33
|
|
Grupa: Zarejestrowani Postów: 1 707 Pomógł: 266 Dołączył: 3.07.2012 Skąd: Poznań Ostrzeżenie: (0%) |
Chyba rzeczywiście jest coś w tym co mówisz, ale źle to argumentujesz. Zrobiłem testy i usunięcie unset nic nie zmienia. Jest za to jedno "ale" - różnica w ilości pamięci pojawia się, gdy użyjemy memory_get_usage() zamiast memory_get_usage(true). Tutaj rzeczywiście unset($e) powoduje, że pamięć nie rośnie, podczas gdy bez unset rośnie.
Pytanie jeszcze o co chodzi z tym parametrem w memory_get_usage, bo wg dokumentacji jest to: Cytat real_usage Set this to TRUE to get total memory allocated from system, including unused pages. If not set or FALSE only the used memory is reported. W praktyce ustawienie go na true nie uwzględnia wielkości stosu, więc albo im się coś popieprzyło, albo ja czegoś nie rozumiem. |
|
|
6.02.2018, 19:56:49
Post
#34
|
|
Grupa: Zarejestrowani Postów: 3 033 Pomógł: 366 Dołączył: 24.05.2012 Ostrzeżenie: (0%) |
przy
Kod 582 366144 FAIL 583 366144 FAIL 584 366144 FAIL 585 366144 FAIL 586 366144 FAIL 587 366144 FAIL 588 366144 Ten parametr w zasadzie nic nie zmienia, tylko mamy trochę większe zużycie ale ono nie rośnie dzięki temu że kasujemy referencje do poprzedniego. Cytat It is because exceptions include a backtrace, containing all the arguments given to the error handling closure. The fifth argument of ErrorException given is $context, an array containing all local variables, including the previous $e. Cytat Pytanie jeszcze o co chodzi z tym parametrem w memory_get_usage, bo wg dokumentacji jest to: W źródle dokładnie to wygląda tak: Kod if (real_usage) {
return AG(mm_heap)->real_size; } else { size_t usage = AG(mm_heap)->size; return usage; } Ten post edytował com 6.02.2018, 20:05:26 |
|
|
6.02.2018, 20:10:33
Post
#35
|
|
Grupa: Zarejestrowani Postów: 1 707 Pomógł: 266 Dołączył: 3.07.2012 Skąd: Poznań Ostrzeżenie: (0%) |
Ten parametr w zasadzie nic nie zmienia, tylko mamy trochę większe zużycie ale ono nie rośnie dzięki temu że kasujemy referencje do poprzedniego. Jak się dokładniej przyjrzałem, to ten parametr z true zwraca o wiele większą ilość pamięci (true: 2 MB, false: niecałe 400 KB). Daję Ci punkciki Pomógł, bo rzeczywiście naprowadziłeś mnie na rozwiązanie problemu, a właściwie udowodniłeś to, co sam podejrzewałem. No to teraz już wiem jak sprawić, żeby mój crawler się nie dławił |
|
|
6.02.2018, 20:15:45
Post
#36
|
|
Grupa: Zarejestrowani Postów: 3 033 Pomógł: 366 Dołączył: 24.05.2012 Ostrzeżenie: (0%) |
|
|
|
7.02.2018, 13:30:13
Post
#37
|
|
Grupa: Zarejestrowani Postów: 1 707 Pomógł: 266 Dołączył: 3.07.2012 Skąd: Poznań Ostrzeżenie: (0%) |
Dzisiaj całą noc chodził crawlerek bez żadnej zadyszki
|
|
|
7.02.2018, 21:12:53
Post
#38
|
|
Grupa: Zarejestrowani Postów: 3 033 Pomógł: 366 Dołączył: 24.05.2012 Ostrzeżenie: (0%) |
super ciekawe co tam crawlujesz
|
|
|
8.02.2018, 11:30:29
Post
#39
|
|
Grupa: Zarejestrowani Postów: 2 885 Pomógł: 463 Dołączył: 3.10.2009 Skąd: Wrocław Ostrzeżenie: (0%) |
Cytat It is because exceptions include a backtrace, containing all the arguments given to the error handling closure. The fifth argument of ErrorException given is $context, an array containing all local variables, including the previous $e. Hmm... pół giga tekstu backtrace'u dla bieżącego i poprzedniego wyjątku + zawartość zmiennych lokalnych. To ile łącznie wyjątków zostało rzuconych? Ciężko w to uwierzyć, że to jest faktyczna przyczyna problemu. -------------------- Nie pomagam na pw, tylko forum.
|
|
|
8.02.2018, 14:48:23
Post
#40
|
|
Grupa: Zarejestrowani Postów: 1 707 Pomógł: 266 Dołączył: 3.07.2012 Skąd: Poznań Ostrzeżenie: (0%) |
Czy ja wiem czy takie dziwne?
Zrobiłem jeszcze jeden test:
Mam dane dla różnych liczb faili i w zależności czy unset był włączony czy nie:
Czyli przy stu failach, var_dump z usuniętym nadmiarem białych znaków ma 673 KB. Każdy fail dodaje do pamięci na przykład pełną informację o $_SERVER, a to swoje waży. Co więcej, w moich testach są tylko nieudane file_get_contents. Zauważyłem, że w pamięci nie ma wcale HTML-a z tych nieudanych, tylko właśnie z poprzedniej wartości - tej udanej. Czyli w moim teście HTML-a nie było wcale w pamięci. W kolejnym teście zrobiłem tak, że naprzemiennie występuje prawidłowy i nieprawidłowy URL. I tutaj uwaga! Przy braku unset i zaledwie 10-ciu failach, rozmiar pliku wzrósł z 72 KB do... 6 MB! Właśnie dlatego, że dla każdego wyjątku była doklejona poprzednia wartość $html. Wniosek: najlepszym rozwiązaniem wydaje się rzeczywiście unset($exception), ale unset($html) też w dużym stopniu pomaga. Ten pierwszy sprawia, że zużycie pamięci w ogóle nie rośnie z kolejnymi failami, a ten drugi sam z siebie zmniejsza znacznie pamięć zabieraną przez wyjątki, ale zużycie nadal rośnie i w końcu się przepełni. @darko jak widać ilość pamięci zabieranej przez wyjątki jest tu na tyle duża, że nie ma co wątpić. Przy setkach tysięcy iteracji to się niestety zsumuje do tych 500 MB, nawet z unset($html). Ten post edytował SmokAnalog 8.02.2018, 14:53:10 |
|
|
Wersja Lo-Fi | Aktualny czas: 26.04.2024 - 15:09 |