воскресенье, 22 февраля 2009 г.

Google Blogger после Livejournal

После 5 лет жизни в ЖЖ, переехал в Blogspot. Итак впечатление следующие:
1. Практически полная свобода творчества по оформлению блога. В ЖЖ огромное множество ограничений (на бесплатных аккаунтах).
2. Интеграция с сервисами Google решает. Очень удобно размещать фотографии в Google Picasa. Наблюдать статистику в Google Webtools и смотреть посещаемость в Google Analytics. А при желании можно добавить Google AdSense. На все про все один аккаунт от google.
3. Нет lj-cut. При желании это решается, но мне не особо и нужно.
4. С одного аккаунта можно вести множество блогов. В ЖЖ для этого надо было перелогиниваться. В блоггере отношение между журналами и авторами - многие ко многим. Тоесть один журнал может вести множество авторов и каждый автор может вести множество журналов.
5. Индивидуальность.

Основные заблуждения про Google Sites

Почитав форумы и попробовав Google Sites вживую, становится понятно, что основными заблуждениями являются:
1. Google Sites не поддерживают домены пользователя. Это не так. В Google Sites можно замэппить любую часть сайта на любой доступный домен.
2. Google Sites позволяет создавать сайт наполняя его любым легальным контентом. Это не так. Нужно быть осторожным, так как например размещение AdSense блоков запрещено соглашением. И при нарушении данного соглашения, ваш сайт будет удален.

суббота, 21 февраля 2009 г.

Google Blogger & AdSense

Blogspot имеет встроенные механизмы для размещения контекстной рекламмы AdSense. Но по ряду причин встроенный механизм мне не подошел (например, он не дает возможность прицепить каналы для мониторинга активности того или иного блока). С другой стороны, Google Blogger позволяет редактировать HTML Template блога и вставлять туда произвольный код в том числе и любой Javascript. Этим грех не воспользоваться для размещения AdSense кода, сгенерированного в панели управления Google Adsense. Казалось бы все просто, но я потерял 3 часа пытаясь понять, почему код блока, сгенерированный в Google Adsense и вставленный в окне HTML Template, не работает. Вместо рекламы или хотя бы социальной рекламы я наблюдал пустое пространство совсем даже не того размера, который задавал. Разбор полетов, в том числе с помощью firebug'а показал, что на запрос к http://googleads.g.doubleclick.net, гугл возвращал код 400 Bad Request. Почему это запрос плохой - adsense сервер сообщить не потрудился. Дальнейшее сравнение видов запроса с работающего блока и запроса с неработающего блока показало, что неработающий блок в запросе не сообщает идентификатор клиента и прочую информацию такого рода. Подозрение пало на джаваскрипт, в котором эти параметры определяются. Код, который генерирует AdSense выглядит примерно так:
<script type="text/javascript"><!--
[... код в стиле var бла=бла-бла-бла; ...]
//-->
</script>

На первый взгляд, все выглядит правильно. Но подозрение закралось на <!-- и //-->. Убрал эти элементы, которые по идее должны помогать браузерам, не поддерживающим джаваскрипт. И о чудо! Блок заработал. Но гугл говорит, что их код править нельзя. Тут у меня закралось еще одно подозрение и в окошке HTML Template гугловский код я записал вот так:
<script type="text/javascript">&lt;!--
[... код в стиле var бла=бла-бла-бла; ...]
//--&gt;
</script>

Это и оказалось правильным решением проблемы.

Вероятное обьяснение: судя повсему, сначало парсер Blogspot'а разбирает template, а потом его форматирует обратно в HTML. При этом переводы строк внутри комментариев <!-- --> он не сохраняет, а рендерит одной строкой в HTML. В результате весь java код выкусывает парсером браузера.

среда, 4 февраля 2009 г.

Microsoft Windows Environment

Каждый раз перезжая на новое рабочую машину, я думаю - это последний раз, больше не придется.

1. Установить http://virtuawin.sourceforge.net/ и назначить переключение рабочих столов на Win-0 ... Win-9 - как общие столы.
Win-C для стола с Eclipse.
Win-I для всяких чатов.

2. Установить http://www.skynergy.com/hotkeyz.html
Назначить Win-z для запуска rxtv с zsh
Назначить Ctrl-Shift-f12 на закрытие окна
Win-Enter - maximize window
Shift-Win-Enter - restore window

3. Установить http://www.cygwin.com/ с пакетами python, perl, zsh, diff, patch, make, mc и еще кучей ползеных программ и утилит.

4. Если вдруг оказалось, что cygwin считает домашней директорией сетевой диск и из-за этого тормозит, то незабыть поменять home директорию в /etc/passwd

5. В /etc/passwd прописать /usr/bin/zsh А в домашнюю директорию положить .zshrc следующего содержания:

alias ls='ls --color'
alias ll='ls -l --color'
alias dfh='df -h'
alias duh='du -h'
alias rm="rm -i"
alias mc="mc -a"

alias c="cd /cygdrive/c"

alias cdp='cd /cygdrive/c/projects/'

export INPUTRC=$HOME/.inputrc

export HISTSIZE=80000
export HISTFILE=~/.history
export SAVEHIST=80000

setopt hist_ignore_dups append_history bsd_echo multios
setopt hist_ignore_all_dups
setopt SHARE_HISTORY

prompt=`echo -ne "%{\033[31m%}%n@%M:%B%30<..<%~%#%b "`

export EDITOR=vim

unsetopt beep

# ##########################################################################3
# -+--+-+ --+-+-

bindkey "\e[1~" beginning-of-line
bindkey '\eOH' beginning-of-line
bindkey "\e[2~" end-of-history
bindkey "\e[3~" delete-char
bindkey "\e[4~" end-of-line
bindkey "\eOF" end-of-line
bindkey "\e[5~" history-incremental-search-backward
bindkey "\e[6~" history-incremental-search-forward
bindkey "\e[A" history-beginning-search-backward
bindkey "\e[B" history-beginning-search-forward
bindkey "\e[C" forward-char
bindkey "\e[D" backward-char
bindkey "\e[7~" beginning-of-line
bindkey "\e[8~" end-of-line
bindkey "\e[3~" backward-delete-char
bindkey "\e[3~" delete-char


# ###########################################################################
chpwd precmd () {
laststatus=$?
[[ $laststatus != 0 ]] && print "\033[1,33m**** \033[1,31mExit code: $laststatus\n"

[[ -t 1 ]] || return
case $TERM in
*xterm*|*rxvt*|*(dt|k|E)term*) print -Pn "\e]2;%n@%M:%15<..<%~%<<\a"
;;
esac
}

preexec () {
[[ -t 1 ]] || return
case $TERM in
*xterm*|*rxvt*|*(dt|k|E)term*) print -Pn "\e]2;%n@%M:%15<..<%~%<< (%15>..>$1%>>)\a"
;;
esac
}

chpwd

# The following lines were added by compinstall

zstyle ':completion:*' completer _expand _complete
zstyle ':completion:*' expand prefix suffix

autoload -Uz compinit
compinit -u
# End of lines added by compinstall

6. В c:/cygwin положить файлик rxvt.bat:
@echo off

C:
chdir C:\cygwin\bin

set CYGWIN=codepage:oem tty binmode title
set TERM=cygwin
rxvt -geometry 90x30 -bg black -fg white -sr -sl 5000 -fn 10x20 -e c:/cygwin/bin/zsh --login -i

суббота, 22 ноября 2008 г.

.ля

6 месяцев назад, сделал в VirtualBox'е snapshot виртуальной машины в которой запускаю виндовые проги. Сегодня решил этот снапшот убить. И убил актуальное состояние. В результате у меня больше нет вещей спроектированных и созданных собственными руками -- схемы и разведенные печатные платы. Особенно жалко:
1. 1-wire датчик влажности и температуры + 1-wire интерфейс к датчику движения.
2. 1-wire датчик PH (ph-метр) на двух ОУ.
3. Библиотека использованных компонент для Altium Designer'а...

Все это и еще многие другие схемы я планировал выложить в блог... Грустно. Несмотря на то, что все эти схемы вытравлены и реализованы в "железе", некоторые из них мне нужно будет делать повторно....

Принимаю соболезнования.

вторник, 12 августа 2008 г.

N560

Звук и кнопки на КПК после дождя плохо себя ведут. Сегодня решил с этой проблемой что-то сделать.

Открывать КПК как-то стремно стало. Боюсь, что обратно я его соберу с еще большими повреждениями. Решил забить на встроенный динамик. При желании можно и наушники для громкой связи использовать задрав громкость до предела. Не выход конечно... А вот с клавиатурой все печальнее. Сначало я думал, что на каждое нажатие кнопки приходит два скан кода один за другим. И думал, что смогу отрезать второй, который приходит слишком рано. Благо перехват скан кодов уже реализован в LooxLight'е. А тут оказалось все куда печальнее. Там не два скан кода приходит. А один "одновременный". Как бы это описать. Ну вот PC клавиатуре там настоящие скан коды. А в клавиатуре КПК, там просто значение у которого каждый бит занчит нажатую кнопку. Значение состоит из двух слов, старшее для стрелочек, а младьшее для всех остальных кнопок. И вот я по логам LooxLight'а наблюдаю следующую картину:
2003.01.02 17:33:38.0000: 6f7dacca: 8f7ddf4c: Char 00040004, cur=00000004, next=00000005, 8f7ddf4c, 8f7ddc64
И так на каждое нажатие. На любое нажатие левое слово = правое. В результате нажимаем стрелочку влево, а получаем и влево и еще какое-то нажатие. И наоборот. Короче хрен обьяснишь. Думаю это как-то завязано на то, что такие клавиатуры обычно реализуются через "матрицу" контактов или хз как и какие-то две ветки там замыкает. А может я и не прав. Сейчас сделаю временное решение, чтобы дисплей хоть разблокировать можно было, а потом буду думать...

Временное решение:
Сравнивать коды клавиш таким образом, что fix(нажатой кнопки) == fix (образца):

UINT fix (UINT x) {
UINT y = (x & 0xFFFF) | (x >> 16);
return y | (y << 16);
}

понедельник, 11 августа 2008 г.

Зедаржки в Java

Так как для задач управление домашней автоматикой я сделал не совсем очивидный выбор - Java, то, естественно, мне было необходимо настраивать работу Java приложения под требование иметь минимальные задержки на события. В результате, для того, чтобы получить имеющийся результат, пришлось предпринять следующие действия:

1. Пускать приложение с schedtool -n -20 -R -p 1 -e /opt/mywire/bin/mywire
Данная команда позволяет запустить приложение в realtime группе с приоритетом 1. Все приложение linux имеют приоритет 0 независимо от nice level'а. Таким образом работа нашего mywire всегда приоритетнее любой задачи.

2. В некоторых критичных нитях, с помощью обращения к native методу происходит установка приоритета в значение 40. Таким образом внутри самого приложения нити имеют разные приоритеты. Это опасно и может привести к блокировкам!

3. Для того, чтобы ни в коем случае mywire не оказался в свопе, память лочится с помощью обращения к native методу mlockall.

4. Сам java процесс пускается со следующими опциями:

-Xms30m -Xmx64m -XX:PermSize=15m -XX:MaxPermSize=30m
-XX:+UseTLAB -jvm server
-XX:MaxGCPauseMillis=20 -XX:+UseConcMarkSweepGC -XX:+CMSIncrementalMode
-XX:+CMSClassUnloadingEnabled
-XX:+ExplicitGCInvokesConcurrentAndUnloadsClasses
-XX:+BackgroundCompilation

Количество памяти, которое я отдаю под heap выбранно таким образом, чтобы сразу после сборки мусора (full gc), свободной памяти было где-то 60%.

Надеюсь ничего не забыл. Как результат мы имеем задержки порядки 10-16мс. При том, что библиотека quartz сама работает с дискретеностью в 10мс. Тоесть если ей сказать, что таску нужно запустить через 5мс, она ее все равно запустить через 10.

К сожалению раз в час происходит full gc или что-то типа того и это влечет за собой неожиданные задержки. Величина зависит от того, как совпадут время срабатывания и начало сборки мусора. В среднем это 200мс. Бывает и 500мс и 700мс. Будем думать как это побороть.

Вот графики:
Latency:


Память.


Видно, что в момент сборки мусора был всплеск задержек.

Предугадывая вопросы:
Java - чтобы писать быстрее.

Latency - в данном случае, это разница времени момента срабатывания таймера и времени, в которое данный таймер должен был сработать. Тоесть, например, если было сказано спать 100мс, а таймер проспал 120мс, то задержка 20мс.

Важность Latency заключается в том, что опрашивать некоторые датчики необходимо весьма часто, скажем датчик движения 2 раза в секунду. В моем варианте датчик движения замыкает размыкает контакты конденсатора давая ему зарядится, таким образом датчик напряжения 1-wire успеет заметить какой-нибудь заряд, даже если он пропустит сам импульс. Так вот если Latency будет слишком высокой (скажем 2-3 секунды), то срабатывания датчик может просто остаться незамеченным.

Кто озадачился вопросом, почему датчик движения не может сам сообщить о срабатывании, отвечу: 1-wire сеть может иметь только одного master'а, все остальные slave'ы.