Home
Objective Caml
ocaml@conference.jabber.ru
Среда, 25 января 2012< ^ >
f[x] установил(а) тему: OCaml / ОКамл / Камль -- http://caml.inria.fr | http://camlunity.ru/ (теперь с git доступом!) | Верблюды грязи не боятся! | release crap, enjoy NIH | репортьте баги официальным дилерам | ocaml мёртв и тормозит, move on | stdlib only? - ССЗБ | Fight FUD with fire
Конфигурация комнаты
Участники комнаты

GMT+4
[00:12:14] <bobry> Kakadu: ты в каком редакторе на камло пишешь?
[00:40:37] dzhon вышел(а) из комнаты
[00:42:39] <Kakadu> bobry: emacs
[00:52:01] <gds> кому трэшака?  налетай!  http://paste.in.ua/3783/
[01:02:37] <bobry> gds: поверить что это еще и работает сложно
[01:11:42] <gds> конечно, что-то может и вылезет.  как раз проверкой и займусь.
[01:18:44] Kakadu вышел(а) из комнаты
[01:29:12] <gds> bobry: удивляюсь тебе!  и как ты только углядел там багу?  вот же ж "глаз-алмаз"!  тебе на шелле писать надо, много денег заработаешь.
[01:36:36] Typhon вошёл(а) в комнату
[02:14:31] <gds> гы, а после мелких фиксов -- реально всё работает в шелл дсл.  создал тупой проект во временной дире, натравил скрипт туда, и он собирает и культурно работает с with (with dir, with env).  даже через "set -x" проверил, где шелл пишет всё, что исполняет.
[02:39:35] f[x] вышел(а) из комнаты: Computer went to sleep
[03:04:25] Typhon вышел(а) из комнаты: Replaced by new connection
[03:04:28] Typhon вошёл(а) в комнату
[03:08:11] komar вышел(а) из комнаты
[03:09:02] komar вошёл(а) в комнату
[03:16:15] Typhon вышел(а) из комнаты: Replaced by new connection
[03:16:17] Typhon вошёл(а) в комнату
[03:25:18] gds вышел(а) из комнаты
[03:27:08] letrec вошёл(а) в комнату
[03:27:12] letrec вышел(а) из комнаты
[03:27:28] letrec вошёл(а) в комнату
[04:00:32] Typhon вышел(а) из комнаты
[04:39:05] letrec вышел(а) из комнаты
[11:25:43] dzhon вошёл(а) в комнату
[12:05:18] klapaucius вошёл(а) в комнату
[12:09:20] ermine вошёл(а) в комнату
[12:10:39] bobry вошёл(а) в комнату
[12:11:45] ftrvxmtrx вошёл(а) в комнату
[12:13:59] ftrvxmtrx вышел(а) из комнаты
[12:47:39] Kakadu вошёл(а) в комнату
[12:54:22] dzhon вышел(а) из комнаты
[13:12:55] dzhon вошёл(а) в комнату
[13:28:59] komar вышел(а) из комнаты
[13:31:06] Kakadu вошёл(а) в комнату
[13:38:50] gds вошёл(а) в комнату
[13:55:59] <ermine> Kakadu: как парсинг? новые идеи появились?
[13:56:26] <Kakadu> ermine: пытаюсь сделать персер арифметики с токенизацией
[13:56:28] <Kakadu> ка ты и сказала
[13:56:57] Kakadu сел на плечико ermine и благодарственно чирикает
[14:01:49] <ermine> не поняла
[14:01:57] <ermine> то есть ты просто взял идею < > ?
[14:02:28] <ermine> идея тоже не моя, увидела в другом парсере
[14:02:42] <Kakadu> ermine: идею про парсер с токенизацией
[14:03:53] <ermine> lexing?
[14:04:00] <Kakadu> угу
[14:04:15] <ermine> а
[14:04:25] <ermine> ну это чисто CF путь
[14:04:31] <f[x]> отставить чириканье в чате!
[14:06:03] <ermine> теперь бы кто мне подсказал, чо делать с параметрами
[14:07:17] Typhon вошёл(а) в комнату
[14:30:36] <ermine> надо погуглить
[14:37:19] <Kakadu> а что там у тебя с параметрами?
[14:41:34] <ermine> посмотри в любой файл .peg в моем архиве и задайся вопросом, как бы ты описал правило с функцией, например spaces(n) <- Space * n, где * n - это взять из инпута n пробелов, вопрос в том, как сразу в такой синтаксис вписать семантику
[14:43:07] <ermine> нет, не так
[14:43:39] <ermine> лучше функция, которая матчит параметр и выдает следующий нетерминал
[14:44:49] <Kakadu> Вроде в нашем проекте такого нет.
[14:45:30] <ermine> ну вот я и застряла
[14:46:01] <ermine> генерить код для этого случая просто, вопрос - как описывать, чтобы можно было вставить семантику
[14:47:36] dzhon вышел(а) из комнаты: Replaced by new connection
[14:47:36] dzhon вошёл(а) в комнату
[14:48:16] <ermine> вопрос чисто художественный
[14:52:59] <ermine> Kakadu: а как в вашем проекте "взять n пробелов, где n =< m"?
[14:53:29] <Kakadu> я не уверен что в параметрах правила можно передавать такие значения
[14:53:32] <ermine> задачу не я придумала, это из спеки по yaml
[14:55:23] <ermine> Kakadu: ну любой комбинатор можно научить брать любое число аргументов, хитрее сделать так, чтобы "недостающие" аргументы выстроились в хвосте функции, которому передаешь комбинаторы, например, как это в unparsing принтере сделано
[14:56:05] <ermine> но вопрос опять не в этом, а в том, как описывать это в грамматике, добавив семантику прямо в грамматику
[14:57:27] <ermine> щас у меня в грамматике все action - просто трансформеры результата цепочки нетерминалов, ну транслятор результата короче
[14:58:02] <ermine> Expr <- Int "+" Int { fun (i1, i2) -> i1+i2 }
[14:58:59] <ermine> тут Int не берет параметры, но легко сделать синтаксис Int(n), поскольку это не влечет за собой добавления семантики в этом месте
[14:59:20] <ermine> а вот Int(n) <- новое правило - уже требует
[14:59:44] <Kakadu> У нас парвила могут принимать другие парвила и пишется это примено как List <<sep item>>
[15:01:56] <ermine> Kakadu: замени List на match c with | A -> sp | B -> crlf
[15:02:25] <Kakadu> не понял
[15:03:28] <ermine> Kakadu: у тебя List аккумулирует результаты токенов, переданных ему в качестве аргументов, так?
[15:05:02] <ermine> а вот хочу функцию, которая бы брала некий параметр и сказала, какой токен дальше парсить
[15:05:57] <ermine> проблема возникает также из-за камла, где функции не рекурсивные и надо либо весь файл писать как let rec abc = .... до конца, либо сортировать порядок функций
[15:06:12] <ermine> в хаскеле все проще, там очередность функций пофигу
[15:06:48] <ermine> поэтому функция, которая хочет выдать сделующий парсер, должна быть после того парсера
[15:07:17] <ermine> надо бечь с камла на более гибкий язык
[15:08:36] <ermine> gds: какой язык гибче чем камло?
[15:09:14] <f[x]> в машкодах очень гибко
[15:09:26] <f[x]> можно сравнивать строки и числа
[15:09:40] <f[x]> можно монады в регистры запихивать
[15:09:47] <f[x]> а потом оттуда кроликов доставать
[15:10:22] <gds> во, правильно про кроликов.  давно не хватает такой функциональности от камла.
[15:10:51] <f[x]> надо нарисовать багу
[15:11:01] <f[x]> правда на кроликов они вряд-ли согласятся
[15:11:08] <gds> кстати, про гибкость, знакомый похапизд порадовал сегодня:
"
из мира похапэ. передобеденноэ, да.
==
В случае, если вы сравниваетедве строки, содержащие числа,     каждая строка будет преобразована в число  и сравниваться они будут как числа.
==
Весьма мило. Обноружыл после того, как в ответ на '1' == '01' получил True.
"
[15:11:09] <ermine> f[x]: это императивно
[15:11:20] <f[x]> ну хотя бы O_PONIES пусть сделают
[15:12:05] <gds> setregisteropt(eax, O_PONIES)
[15:12:22] <f[x]> gds: про пхп известное же : "11" < "a" < 2 < "11"
[15:12:41] <gds> ой как няшно!  а я и не знал.
[15:13:07] <f[x]> http://php.net/manual/en/language.operators.comparison.php
[15:13:39] <f[x]> как прикоснуться к чуду
[15:13:43] <gds> ой-вэй!
[15:13:54] <gds> с другой стороны, теперь браузер мыть.
[15:14:14] <f[x]> и клавиатуру менять
[15:14:35] <f[x]> > type juggling
[15:14:52] <f[x]> php - never enough
[15:16:19] <ermine> эх
[15:20:22] <Kakadu> ermine: короче я спросил у своих и то что ты хочшеь пока не сделано и фиг знает когда будет сделано
[15:21:12] <ermine> Kakadu: а какие у них соображения?
[15:21:42] <ermine> Kakadu: мне вообще идея нужна
[15:21:44] <Kakadu> потому что над эти надо поломать голову как сделать так, чтобы этот был в action code
[15:21:47] ermine плачет
[15:22:42] <Kakadu> т.е. синтаксис
rule<<n item>> : item [2..n] {} пока в планах
[15:23:05] <Kakadu> а вот
rule<<n item>> : item [2..n]  { print n }
ghjcnj yt gjyznyj rfr cltkfnm
[15:23:11] <Kakadu> просто неппонятно как сделать\
[15:24:10] <ermine> не, я хочу match
[15:24:27] <Kakadu> мэтч вместо принта?
[15:24:55] <ermine> и нетерминал, который выползает из матча
[15:25:05] <ermine> а у тебя все вползают наоборот
[15:25:09] letrec вошёл(а) в комнату
[15:25:14] <Kakadu> я не понимать
[15:26:24] <ermine> Kakadu: скажем так, action, который управляет процессом парсинга, action выдал следующий комбинатор для парсинга
[15:26:41] <ermine> обычно action выдает лишь результат парсинга
[15:26:48] <Kakadu> да у нас так
[15:26:51] <Kakadu> у нас типа как в якке
[15:27:18] <ermine> шо?
[15:27:33] <ermine> а, yacc
[15:28:24] <ermine> вот и думаю как оформить управляющий action
[15:28:51] <ermine> или расширения к парсеру
[15:31:33] <ermine> вот такое вот наркоманство
[15:35:20] <Kakadu> да уж
[15:35:52] <ermine> Kakadu: у вас проект когда начали делать?
[15:36:32] <Kakadu> ой давно
[15:36:37] <Kakadu> больше 3х лет назад
[15:36:54] <Kakadu> сейчас только норм работает парсилка грамматики и генерация fsyacc парсера
[15:37:31] <Kakadu> Ну я своим багу записал про то, что ты хочешь
[15:37:38] <Kakadu> Мож что скажут
[15:37:46] dzhon вышел(а) из комнаты: Replaced by new connection
[15:37:47] dzhon вошёл(а) в комнату
[15:38:01] dzhon вышел(а) из комнаты
[15:38:16] dzhon вошёл(а) в комнату
[15:38:50] <ermine> да я наверное рожу в ближайшее время
[15:39:15] <ermine> у меня проект начался не три года назад, а всего два месяца назад
[15:39:18] <Kakadu> кого родишь?
[15:39:46] <ermine> описание расширений в парсер
[15:40:36] <ermine> щас я везде идентификатор в грамматиках привожу к тому, чтобы он мог быть именем функции
[15:41:47] <ermine> в смысле ident <- (letter / '_') (letter /digit / '_' / '\'')*, как завещала дока по камлу
[15:42:15] <Kakadu> а что такое /
?
[15:42:28] <ermine> до этого я просто прилепляла префикс к идентификатору, который мог начинаться с большой буквы
[15:42:43] <ermine> ой, определение неточное, ну да ладно
[15:43:45] <Kakadu> l_class           <- "["  (!"]" range)* "]"     { fun cs -> Class cs }
вообще неочевидно откуда береться cs
[15:45:42] <ermine> у меня action - это трансформеры результата последовательности, они всегда на конце последовательности
[15:45:56] <Kakadu> а какого типа тогда cs?
[15:46:03] <ermine> генератор выполняет последовательность и сует результат в трансформатор
[15:46:53] <ermine> ну смотришь что могут возвращать части
[15:47:30] <Kakadu> наверное какойто список
[15:47:47] <ermine> нетерминал возвращает либо токенизатор, если в правиле было < >, либо (), если ничего, либо результат самих нетерминалов в правиле как тьюпл
[15:48:03] <ermine> таким образом c <- 'a' вернет ()
[15:48:17] <ermine> c <- < 'a' > вернет лексему
[15:48:44] <ermine> a <- c c c вернет тьюпл (c1, (c2, c3))
[15:48:52] <ermine> в случае с лексемой
[15:49:11] <Kakadu> ага
[15:49:28] <ermine> Kakadu: я тебе в декабре говорила, что сообразила как выяснить как вычислить нужен ли результат или нет
[15:49:50] <Kakadu> я уже всё забыл но да ладно
[15:50:15] <ermine> поэтому не нужны конструкции вида List << abc >>
[15:51:11] <ermine> вместо этого c* - это синтаксис, который имеет значение 'a list и превращается в вызов функции star c или tar_accu c
[15:52:31] <Kakadu> Ну может потому что у тебя всё на комбинаторах у тебя всё это очевидно и по-другому плохо
[15:52:44] <ermine> первое вернет ()б второе - список
[15:53:26] <ermine> поэтому так же отпала необходимость в $1, $2 из yacc
[15:53:57] <ermine> генератор анализирует ast и сам видит всё
[15:54:27] <ermine> ну, щас не без косяков
[16:07:54] <Kakadu> type Parser<'Result, 'UserState> = CharStream<'UserState> -> Reply<'Result>
[16:08:01] <Kakadu> а зачем при парсинге нужен UserState?
[16:11:16] <ermine> если это стэк, то при старте парсинга надо сначала создать стэк и передать парсеру, потом actionы получают этот стэк и могут сами вынимать результаты оттуда и класть новые туда и отправлять стэк дальше
[16:11:33] <ermine> так было у меня в этом комбайне с самого начала, я потом эту модель отвергла
[16:12:31] <ermine> не понравилось, что стэк не полиморфен и поэтому требовались десятки assert'ов
[16:13:29] <ermine> другой вариант - в userstate может быть любое говно, которое нужно экшнам
[16:13:29] <Kakadu> т.е. это типа хак, чтобы в action коде можно было куда-то заглфдывать и на основе этого смотреть что выдавать (ака магазинный автомат)?
[16:13:54] <ermine> это говно просто проползает через всё равномерно
[16:14:48] <ermine> ну да, по идее только action знают тип userstate и его трогают
[16:20:24] <ermine> я userdata потом добавлю в свой генератор, чтобы он прогонял эту хрень через все action, если юзер захочет этого, так сказать, вгенерить on demand, благо что camlp4 рулит
[16:23:25] <Kakadu> а я тут пытаюсь решить проблему нужны ли мне свои парсер-комбинаторы или справлясб с fparsecовским CharStream
[16:26:38] <ermine> дешевлее взять готовое
[16:26:53] <ermine> особенно если ты еще не прочитал какую-нить книжку по парсингу
[16:26:55] <ermine> :)
[16:27:16] <Kakadu> дешевле то дешевле но fparsec парсит стрим чаров а мне надо отпарсить уже оттокенизированное
[16:27:36] <ermine> писать свое - вникать в оптимизацию, выводилку результатов, сортировку и решение конфликтов
[16:28:10] <Kakadu> Ну мне же не для пользы а для папира! (привет gds)
[16:29:02] <ermine> главное, что не диссертация
[16:29:18] <ermine> в диссертации фиг заюзаешь только чужое добро
[16:29:26] <Kakadu> я вот сейчас думаю должно ли быть у потока токенов внутреннее состояние
[16:30:35] <ermine> а что такое внутреннее состояние?
[16:31:05] <ermine> опять же, ты не читал про DFA, NFA и прочие автоматы с управлением и состоянием
[16:32:11] <ermine> кстати, у Stream.of_string есть внутреннее состояние, точнее, у Stream.from
[16:33:21] <Kakadu> Ну вот если я хочу отпарсить А а затем В
[16:33:32] <Kakadu> и у меня А отпарсилось , а В не отпарсилось
[16:33:51] <Kakadu> То надо будет оставить поток токенов который был до парсинга А
[16:33:54] bobry вышел(а) из комнаты
[16:34:51] <Kakadu> А если без внутреннего состояния, то там ге парсер возвращает резултат должен быть Ok от хвоста того, что не распарсилось (как  в итератах)
[16:35:12] <gds> ПАРСЕТОТА
[16:35:53] komar вошёл(а) в комнату
[16:36:15] <ermine> Kakadu: парсер возвращает остаток инпута
[16:36:22] <ermine> это ключевая фраза
[16:37:02] <Kakadu> ermine: в gdsовских итератах, но походу не в FParsec
[16:37:04] <ermine> другая ключевая фраза - последовательность является бинарной операцией
[16:37:59] <ermine> seq A B input = match A input with | Success rest -> B rest | Failed -> тут инпут так и не изменился
[16:39:34] <Kakadu> Ну да, у тебя на выходе хвост инпута, но в fparsec не так
[16:39:49] <ermine> Kakadu: ну итераты у gds не оригиналы и не нарушают сорокалетнюю технологию парсинга
[16:41:27] <ermine> Kakadu: ну там тоже должна быть функция последовательности, которая в случае облома вернет оригинальный инпут
[16:42:18] <Kakadu> ermine: https://bitbucket.org/fparsec/main/src/a7df4d71f533/FParsec/Primitives.fs#cl-73
вот она
[16:43:42] <ermine> грустная монадная нотация
[16:46:15] <ermine> Kakadu: >>= - это бинд, это еще не последовательность
[16:46:56] <Kakadu> там >>,
[16:46:58] <Kakadu> >>.
[16:48:15] <ermine> ну наверное
[17:12:55] dzhon вышел(а) из комнаты
[17:13:07] dzhon вошёл(а) в комнату
[17:18:17] ermine домыслила два из трех случаев use-case своей проблемы с расширением парсера, уже лучше чем ничего, теперь бы последний случай додумать, а выпить опять нечего
[17:21:35] <ermine> добавлю я {. repeat 3 space .}, action, который трогает инпут как обычный парсер и попытается нащупать там три пробела, такой action получит на вход инпут, однако потом опять придется крепко подумать про интерфейс итератов
[17:27:19] <ermine> теперь Action имеет тип of Camlp4.PreCast.Ast.expr
[17:31:22] dzhon вышел(а) из комнаты
[17:46:46] ermine ищет чем бы to_stringовать Ast.expr
[17:51:49] <Kakadu> ermine: и вот в какой момент комбинаторы должны проверять что вход пустой?
[17:52:21] <Kakadu> наверное во всяких высокоуровневых функциях типа >>. не надо а надо в низкоуровневых типа parse_float?
[17:56:31] <ermine> пустой вход - классический вопрос
[17:57:04] <ermine> в итератах это EndOfFile, а не Chunk input будет
[17:57:54] <ermine> у меня в парсинге в peg определено, что . - это вообще любой символ инпута, поэтому !. - это предикат, который отрицает наличие любого символа
[17:58:28] <ermine> соответственно это комбинатор, который скажет да или нет это конец файла
[17:58:48] <ermine> и вызывается при каждом щупании инпута
[17:59:08] <ermine> всё так же с любым флоатом и пр
[17:59:51] <ermine> Kakadu: подели комбинаторы на трогающие инпут и не трогающие сами инпут, а только вызывающие другие комбинаторы
[18:00:56] <Kakadu> ага, по такой сортировке >>. не трогает инпут, так?
[18:01:41] <ermine> ага
[18:36:39] <Typhon> gds: я немножко выпадал, а просвети, пожалуйста, какой сейчас статус итерат-туториала? ты пишешь что-то или ждёшь фидбека? я посмотрел сейчас — вроде строк больше чем было, но может не сильно, вечером буду перечитывать. но может что-то ещё есть? :-)
[19:42:18] <gds> Typhon: статус таков: 1. отписал с прошлых пор ещё, пока "запала" хватило, 2. запал закончился из-за отсутствия фидбэка -- такое впечатление, что пишешь китайскую грамоту для японцев на русском языке; ну и реально непонятно, понимают ли люди, 3. была куча других дел, я тоже выпадал, только не так глобально, но возвращался с выеденным мозгом, 4. про твой фидбэк на тему "нужно больше примеров вместо скучного матана" я не знаю, что сказать, так как примеры будут казаться какой-то непонятной магией, и не будет понятно, как это всё работает, не разобрав принципы и простые итераты.  то есть, в данном вопросе я склоняюсь к "строить с глубокого фундамента и строго вверх".  но, если чо, давай обсуждать этот вопрос.
[19:42:28] Kakadu вышел(а) из комнаты
[19:42:57] Kakadu вышел(а) из комнаты
[19:45:57] <f[x]> страшно далеки они были от народа
[19:48:09] <gds> ну как сказать.  нормальная обработка потоков -- это всё-таки не рокетсаенс в плане практики, это всем нужно, кто не только в бирюльки играется.
[20:16:31] dzhon вошёл(а) в комнату
[20:30:49] ftrvxmtrx вышел(а) из комнаты
[20:40:48] Kakadu вошёл(а) в комнату
[20:46:12] komar вышел(а) из комнаты
[20:46:42] komar вошёл(а) в комнату
[21:15:14] letrec вышел(а) из комнаты
[21:50:09] f[x] вошёл(а) в комнату
[22:05:08] Typhon вышел(а) из комнаты
[22:32:18] ermine сходила в гости выпить и там поняла, что мешает идее мержения грамматики с семантикой из отдельных файлов: наличие в грамматике альтернатив посередине последовательностей: в грамматике у camlp4 таких свобод нет, как ни странно, в смысле, там нельзя | A (C|D) F прописать
[22:32:28] <ermine> хитер хренцуз, всё заранее обдумал!
[22:34:30] <bobry> «The Objective-Caml bytecode interpreter was faster than the carefully hand-optimized C program! Why? Because the OCaml compiler could recognize that the arrays were completely independent - it didn't need to worry about one iteration of the loop stepping on the values used by another. The C compiler couldn't apply a lot of useful optimizations, because it couldn't be sure that they were valid.»
[22:34:34] <bobry> http://scienceblogs.com/goodmath/2006/11/the_c_is_efficient_language_fa.php
[22:38:09] <Kakadu> bobry: копипаст откуда не помню
[22:38:10] <ermine> любят они всё сувать в массивы
[22:38:19] <ermine> даже модули, а не только флоаты
[22:44:40] <ermine> а нонче модно компилить в нативе, а не байткоде, потому что так еще быстрее будет работать
[22:49:46] dzhon вышел(а) из комнаты: Replaced by new connection
[22:49:46] dzhon вошёл(а) в комнату
[23:10:49] <bobry> ermine: ну модули грех в массив не сунуть, first class же
[23:14:14] Typhon вошёл(а) в комнату
[23:14:53] <ermine> first order
[23:16:50] <ermine> Kakadu: а напомни плиз ссылку на ваш проект парсинга
[23:19:34] <Kakadu> http://code.google.com/p/recursive-ascent/
[23:23:14] <ermine> пейсиб, закопала ссылку, изучу завтра
[23:23:29] <ermine> а щас опять гуглю на тему "merge grammar and semantic"
[23:27:48] bobry вышел(а) из комнаты
[23:31:11] <ermine> мда, за 50 лет понаписали разных бумажек на тему, как кушать текст
[23:31:22] bobry вошёл(а) в комнату
[23:31:28] <ermine> 50 лет назад было явно легче
[23:39:08] komar вышел(а) из комнаты
[23:42:38] komar вошёл(а) в комнату
[23:44:10] <gds> а пару сотен лет назад было ещё легче -- не нужно было думать, как изготавливать туалетную бумагу.
[23:45:12] <ermine> Kakadu: почитай доку по Bison, там есть классная разжевалка как у них работает (la)lr или glr
[23:46:34] <ermine> gds: я где-то читала, что ученые до сих пор не выяснили, чем до туалетной бумаги люди подтирались
[23:47:46] <gds> в некоторых случаях -- камнем, исторический факт.  кто чем мог -- лопухом, пальцем, в водоёме подмылся.  впрочем, мелочи.  раньше было проще, точно.
[23:49:38] <ermine> хорошо жить в африке, где лопухи растут круглый год
[23:50:09] <ermine> а вот в городах средневековья?
[23:50:53] <gds> думаешь, почему там выдумали парфюм?  вот как раз для этого.
[23:52:46] <gds> я бы вообще много сказал про дебилов, ратующих за "золотой век", "рыцарское средневековье", но дебилы меня не услышат, а вам это как бы оффтопик, ибо ocaml@cjr
[23:52:49] <ermine> для подтирки?
[23:53:02] <gds> для подтирки банальных желёз11111
Powered by ejabberd Powered by Erlang Valid XHTML 1.0 Transitional Valid CSS!