Почему Git.pm на cygwin жалуется на «Недостаточно памяти во время« большого »запроса? - PullRequest
13 голосов
/ 17 декабря 2009

Я получаю эту ошибку при выполнении git svn rebase в cygwin

Out of memory during "large" request for 268439552 bytes, total sbrk() is 140652544 bytes at /usr/lib/perl5/site_perl/Git.pm line 898, <GEN1> line 3.

268439552 - 256 МБ. Максимальный объем памяти Cygwin установлен на 1024 МБ, поэтому я предполагаю, что он имеет другой максимальный объем памяти для perl?

Как увеличить максимальный объем памяти, который могут использовать perl-программы?

обновление: Вот где происходит ошибка (в Git.pm):

 while (1) {
      my $bytesLeft = $size - $bytesRead;
      last unless $bytesLeft;

      my $bytesToRead = $bytesLeft < 1024 ? $bytesLeft : 1024;
      my $read = read($in, $blob, $bytesToRead, $bytesRead); //line 898
      unless (defined($read)) {
         $self->_close_cat_blob();
         throw Error::Simple("in pipe went bad");
      }

      $bytesRead += $read;
   }

Я добавил печать перед строкой 898, чтобы распечатать $ bytesToRead и $ bytesRead, и результат составил 1024 для $ bytesToRead и 134220800 для $ bytesRead, поэтому он читает 1024 байта за раз и уже прочитал 128 МБ. Функция Perl 'read' должна быть не в памяти и пытается запросить удвоение своего объема памяти ... есть ли способ указать, сколько памяти запрашивать? или это зависит от реализации?

UPDATE2: При тестировании выделения памяти в cygwin: Выход этой программы на C был 1536MB

int main() {
   unsigned int bit=0x40000000, sum=0;
   char *x;

   while (bit > 4096) {
      x = malloc(bit);
      if (x)
         sum += bit;
      bit >>= 1;
   }
   printf("%08x bytes (%.1fMb)\n", sum, sum/1024.0/1024.0);
   return 0;
}

Хотя эта Perl-программа аварийно завершала работу, если размер файла превышал 384 МБ (но успешно, если размер файла был меньше).

open(F, "<400") or die("can't read\n");
$size = -s "400";

$read = read(F, $s, $size);

Ошибка похожа

Out of memory during "large" request for 536875008 bytes, total sbrk() is 217088 bytes at mem.pl line 6.

Ответы [ 4 ]

9 голосов
/ 28 сентября 2011

Эта проблема была решена в последней версии msysgit Грегором Уленхойером . Доступен патч. Проблема в том, что в Git.pm файл читается за один раз. Решение состоит в том, чтобы прочитать это маленькими кусками. Я не уверен, что исправление вошло в какие-либо выпущенные версии, но его легко применить локально.

Вам нужно изменить C: \ Program Files \ Git \ lib \ perl5 \ site_perl \ Git.pm (смена около 8 строк). Сначала убедитесь, что вы сделали резервную копию.

Подробнее о том, что делать, см. Git.pm: использовать потоковую запись в cat_blob () .

Исходное обсуждение Проблемы с большими файлами "Недостаточно памяти" .

8 голосов
/ 17 декабря 2009

Вы пытались увеличить общую полезную память Cygwin?

Это сообщение показывает, что Perl уже был до 130 МБ (всего sbrk ()), а затем попытался запросить дополнительные 256 МБ, что не удалось.

С http://www.perlmonks.org/?node_id=541750

By default no Cygwin program can allocate more than 384 MB of memory 
(program+data). You should not need to change this default in most 
circumstances. However, if you need to use more real or virtual 
memory in your machine you may add an entry in the either the 
HKEY_LOCAL_MACHINE (to change the limit for all users) or
HKEY_CURRENT_USER (for just the current user) section of the registry.

Add the DWORD value heap_chunk_in_mb and set it to the desired 
memory limit in decimal MB. It is preferred to do this in Cygwin 
using the regtool program included in the Cygwin package. (For 
more information about regtool or the other Cygwin utilities, 
see the Section called Cygwin Utilities in Chapter 3 or use 
each the --help option of each util.) You should always be 
careful when using regtool since damaging your system registry
can result in an unusable system. 
5 голосов
/ 21 мая 2010

Решение с максимизацией памяти Cygwin фактически не работает.

В настоящее время есть две проблемы с Git на Windows:

  1. Упаковки более 2G вряд ли поддерживается либо MsysGit и Cygwin git
  2. память Cygwin по умолчанию сумма слишком мала
  3. 32-битный Git проблемный

Что я сделал шаг за шагом:

Я перенес свое git-репо на Unix-машину, установил следующие конфиги:

[pack]
        threads = 2
        packSizeLimit = 2G
        windowMemory = 512M

После этого я сделал git gc и все колоды были восстановлены до 2G.

Дважды проверил, что MsysGit не установлен на машине с Windows, можно использовать другой способ perl из MsysGit.

Перенес этот репо обратно на Windows Machine и увеличил лимит памяти Cygwin:

regtool -i set /HKLM/Software/Cygwin/heap_chunk_in_mb 1536

Важно было установить память Cygwin выше pack.windowMemory × pack.threads и не выше 1,5G

Итак, первые две проблемы теперь решены. Но третий не.

К сожалению, это не работает на Windows. Во время некоторых перепаковок иногда происходит сбой из-за нехватки памяти. Даже с threads = 1 и pack.windowMemory = 16M и максимальной глубиной и дельтой, установленными на 250.

5 голосов
/ 17 декабря 2009

Это не специфичная для Perl проблема, а связанная с cygwin. Вы можете увеличить выделение памяти с помощью ulimit.

Какую версию Git вы используете? Если вы используете не последнюю версию, это может быть неэффективностью, которая была исправлена ​​в последней версии (например, циклически просматривая очень большой файл с foreach вместо while, как подсказывает Google, когда я выполнял быстрый поиск .)

...