Blog. Just Blog

Образ мышления: Assembler

То, что не удается запрограммировать на Ассемблере, приходится паять
Образ мышления: Assembler - RSS-канал Образ мышления: Assembler - Карта сайта

Проверка и обнаружение зависших приложений

27.10.2009 | Категория: Образ мышления: Assembler | Автор: ManHunter
Иногда для работы требуется определение зависших приложений, окна которых не отвечают на сообщения. Для этого есть два способа. Первый - официально документированный, через функцию SendMessageTimeOut. Особенность ее работы заключается в том, что после отправки сообщения окну она ждет ответ заданное время, и, если ответа от приложения не последовало, то возвращает FALSE. Вот пример использования функции. Нужные константы, как обычно, в FASM не определены, пришлось брать их из других источников.
  1.         ...
  2.         ; Определить таймаут 50 миллисекунд
  3.         TIMEOUT = 50
  4.         ; Определить константу SMTO_ABORTIFHUNG
  5.         SMTO_ABORTIFHUNG = 2
  6.         ; hwnd - хэндл проверяемого окна
  7.         invoke  SendMessageTimeout,[hwnd],NULL,0,0,SMTO_ABORTIFHUNG,TIMEOUT,NULL
  8.         ; Если вернулся 0, то приложение "висит"
  9.         or      eax,eax
  10.         jz      app_hung_up
  11.         ...
Минус использования этой функции в том, что при частой проверке большого количества окон зависших приложений, каждый раз будет отрабатываться таймаут для каждого такого окна, что суммарно может дать снижение производительности вашего приложения. Но повторюсь, Microsoft официально рекомендует к использованию именно эту функцию.

Читать статью целиком »
Просмотров: 8370 | Комментариев: 2

Управление клавишами NumLock, CapsLock и ScrollLock

07.10.2009 | Категория: Образ мышления: Assembler | Автор: ManHunter
Иногда в программах требуется получать состояние управляющих клавиш или изменять их состояние. Во времена MS-DOS достаточно было просто прочитать или записать значение WORD по определенному адресу памяти, при этом светодиодные индикаторы клавиатуры реагировали на это включением или выключением. Были очень популярны крохотные, в несколько байт, программы для выключения NumLock при загрузке системы, типа таких:
  1. ;-----------------------------------------------------------
  2. ; Программа для выключения индикатора NumLock под MS-DOS
  3. ; Размер .com-файла после компиляции 9 байт
  4. ;-----------------------------------------------------------
  5. .286
  6. .model  tiny
  7. .code                         ; Сегмент кода
  8.         org     100h          ; Зарезервировано для PSP
  9. start:
  10.         pop     ax            ; После запуска в стеке 0, AX=0
  11.         mov     ds,ax         ; DS=0
  12.         mov     ds:[417h],ax  ; WORD DS:[417h] - состояние *Lock'ов
  13.         int     20h           ; Выход из программы
  14. end     start
В свое время это был самый минимальный рабочий код для выключения клавиши NumLock, хоть и не совсем корректный в плане работы со стеком.

Читать статью целиком »
Просмотров: 13325 | Комментариев: 3

Подсказки (tooltips) в диалоговых окнах

16.09.2009 | Категория: Образ мышления: Assembler | Автор: ManHunter
Еще один способ придать вашим программам профессиональный вид - использование всплывающих подсказок (tooltips), которые появляются при наведении курсора мыши на какой-нибудь элемент диалогового окна. Готовые примеры на FASM или слишком громоздкие, или недостаточно гибкие, поэтому пришлось придумывать что-то свое. Причем с самого начала поставил себе задачу сделать функции работы с подсказками как можно более универсальными, чтобы в дальнейшем их можно было легко использовать в других проектах.

В сегменте данных определим все необходимые константы, переменные и структуры. Большая часть этих данных в FASM по умолчанию отсутствует, так что пришлось штудировать MSDN и другие источники и описывать их самостоятельно.
  1. ; Сегмент данных
  2. section '.data' data readable writeable  
  3.  
  4. hwndTip         dd ?    ; Хэндл окна подсказки
  5. TTipFlag        dd ?    ; Флаг активности подсказки
  6.  
  7. ; Структура TRACKMOUSEEVENT не определена, сделаем это сами
  8. struct TRACKMOUSEEVENT
  9.   cbSize        dd ?
  10.   dwFlags       dd ?
  11.   hwndTrack     dd ?
  12.   dwHoverTime   dd ?
  13. ends
  14.  
  15. ; Определяем нужные структуры
  16. tme     TRACKMOUSEEVENT
  17. pt      POINT
  18. ttip    TOOLINFO
  19. trect   RECT
  20.  
  21. oldX    dd ?    ; Сохраненные координаты мыши
  22. oldY    dd ?
  23.  
  24. ; Определяем нужные константы
  25. TTM_TRACKACTIVATE  = WM_USER + 17
  26. TTM_TRACKPOSITION  = WM_USER + 18
  27. TTM_SETMAXTIPWIDTH = WM_USER + 24
  28.  
  29. ; Сообщения окну подсказки
  30. TTF_SUBCLASS       = 0x0010
  31. TTF_TRACK          = 0x0020
  32. TTF_ABSOLUTE       = 0x0080
  33. TTF_TRANSPARENT    = 0x0100
  34.  
  35. ; Сообщение обработчика мыши
  36. TME_LEAVE          = 0x00000002
  37.  
  38. ; Максимальная ширина всплывающей подсказки
  39. TOOLTIP_WIDTH      = 200
  40.  
  41. ; Предустановленное количество элементов в массиве подсказок
  42. TOOLTIPS_COUNT     = 5
  43.  
  44. ; Массив данных для всплывающих подсказок
  45. ; Формат массива:
  46. ;   1 DWORD - сохраненный адрес обработчика
  47. ;   2 DWORD - адрес подсказки
  48. tt_data rd  (TOOLTIPS_COUNT*2)
Для добавления подсказок к элементам диалогового окна я написал отдельную процедуру, использующую субклассирование. Она же является процедурой, создающей исходное окно подсказки, если оно до этого не было создано. Окну подсказки присваивается максимальная ширина, определяемая константой TOOLTIP_WIDTH, и для большей изящности добавляется эффект тени.

Читать статью целиком »
Просмотров: 5754 | Комментариев: 10

Поле EDIT для ввода шестнадцатеричных цифр

23.08.2009 | Категория: Образ мышления: Assembler | Автор: ManHunter
Поле для ввода только цифр организовать несложно, для этого достаточно просто прописать в ресурсах у нужного поля флаг ES_NUMBER. После этого с клавиатуры в это поле можно будет ввести только символ из интервала "0" - "9". Впрочем этот ничуть не мешает через Ctrl+C / Ctrl+V затолкать в него все что угодно, вплоть до непечатных бинарных данных. А как сделать поле, в которое можно вводить с клавиатуры только шестнадцатеричные цифры? Ведь там могут быть не только символы с десятичными цифрами, но и символы "A" - "F", которые также являются шестнадцатеричными цифрами. Это делается через субклассирование. Мы уже рассмотрели один пример субклассирования, превратив поле EDIT в гиперссылку, и там же определили алгоритм обработчика субклассированного элемента. Как и в прошлый раз, субклассирование должно выполняться на этапе инициализации диалогового окна.
  1. ; Сегмент данных
  2. section '.data' data readable writeable  
  3. OldProc dd ?    ; Адрес предыдущего обработчика
  4.  
  5. ; Сегмент кода
  6. section '.code' code readable executable
  7.         ...
  8.         ; Субклассирование на этапе инициализации окна
  9.         invoke  GetDlgItem,[hwnddlg],ID_HEX
  10.         ; Установить наш собственный обработчик
  11.         invoke  SetWindowLong,eax,GWL_WNDPROC,EditWindowProc
  12.         ; Сохранить хэндл предыдущего обработчика
  13.         mov     [OldProc],eax
  14.         ...
Здесь все почти то же самое, разница будет лишь в обрабатываемых сообщениях. Соответственно, если будет несколько полей ввода, то надо субклассировать каждое из них отдельно.

Читать статью целиком »
Просмотров: 6332 | Комментариев: 9

Создание диалоговых окон с тенью

03.08.2009 | Категория: Образ мышления: Assembler | Автор: ManHunter
Сегодня разберем очередное украшательство для ваших программ, а именно тень от диалоговых окон. Обычная тень создается штатными средствами системы, но поддерживается только начиная с Windows XP. Для этого требуется, чтобы стиль окна включал в себя флаг CS_DROPSHADOW, и здесь есть одна тонкость: этот флаг нельзя прописать в ресурсах, а надо устанавливать при инициализации диалогового окна. В обработчике инициализации должен быть такой код:
  1.         ...
  2.         ; Определить константу CS_DROPSHADOW
  3.         CS_DROPSHADOW = 00020000h
  4.         ; Получить текущее значение стиля окна
  5.         invoke  GetWindowLong,[hwnddlg],GCL_STYLE
  6.         ; Добавить к нему атрибут тень
  7.         or      eax,CS_DROPSHADOW
  8.         ; Установить новый стиль окна
  9.         invoke  SetClassLong,[hwnddlg],GCL_STYLE,eax   
  10.         ...
Тут есть плюсы: корректно поддерживаются окна любой нестандартной и сложной формы, а все следующие окна процесса автоматически создаются сразу с тенью. Но есть один странный момент. Несмотря на то, что дочерние окна сперва создаются с корректной тенью, при любом перемещении их над родительским окном тени родительского и дочернего окна сливаются в одну. Пример такого нездорового явления природы показан на скриншоте.

Читать статью целиком »
Просмотров: 6727 | Комментариев: 1

prev 01 ... 64 65 66 67 68 69 70 ... 73 next
Наверх
Powered by PCL's Speckled Band Engine 0.2 RC3
© ManHunter / PCL, 2008-2025
При использовании материалов ссылка на сайт обязательна
Время генерации: 0.07 сек. / MySQL: 2 (0.0046 сек.) / Память: 4.5 Mb
Наверх