Быстрый поиск
Введите фрагмент названия статьи для поиска
Работа с escape-последовательностями на Ассемблере
28.02.2015 | Категория: Образ мышления: Assembler | Автор: ManHunter
Работа с escape-последовательностями на Ассемблере
Escape-последовательности, также известные как экранированные последовательности или символьные объекты, представляют собой особый метод представления символов внутри строк. В зависимости от синтаксиса языка, ими могут кодироваться не только ASCII-символы, но и вся последовательность юникода UTF-16 и даже UTF-32. В процессе компиляции или при отображении на экране каждая escape-последовательность заменяется на соответствующий ей код символа. Кроме этого, такую запись символов очень часто используют в различных обфускаторах для скриптов PHP и JavaScript с целью затруднения визуального анализа текстовых строк или кодирования исходных текстов. Escape-последовательность обычно распознается по начальному символу обратного слеша и фиксированному количеству символов, следующих за ним.
Читать статью целиком »
Просмотров: 5593 | Комментариев: 1
Функции urldecode и urlencode на Ассемблере
30.01.2015 | Категория: Образ мышления: Assembler | Автор: ManHunter
Функции urldecode и urlencode на Ассемблере
Моя реализация функций PHP urldecode и urlencode, а также двух их разновидностей rawurldecode и rawurlencode на Ассемблере. Алгоритм их работы описан в документации. Единственное отличие от оригинальной функции rawurlencode в том, что кодируется вся строка целиком, а не только буквенно-цифровые символы. На мой взгляд, это более логичное поведение функции с приставкой "raw". В остальном никаких отличий нет.
Читать статью целиком »
Просмотров: 5428 | Комментариев: 0
Как преобразовать кириллическую строку из UTF-8 в cp1251
26.10.2014 | Категория: Образ мышления: Assembler | Автор: ManHunter
Как преобразовать кириллическую строку из UTF-8 в cp1251
При разработке одной программы мне понадобилось преобразовать строки на русском языке из формата UTF-8 в формат cp1251. Внезапно выяснилось, что никакие средства WinAPI не позволяются выполнить эту операцию "одной строкой". Пришлось рассматривать даже варианты с табличным преобразованием, но потом нашлось более простое решение задачи. Алгоритм преобразования получился необычный, но зато гарантированно рабочий. Может быть это поможет сохранить время и нервы кому-нибудь еще.
Читать статью целиком »
Просмотров: 9893 | Комментариев: 10
Полезные функции для работы с датами на Ассемблере
05.06.2014 | Категория: Образ мышления: Assembler | Автор: ManHunter
Полезные функции для работы с датами на Ассемблере
Из разных источников насобирал различные полезные функции для работы с датами на Ассемблере. Преимущества их в том, что они работают очень быстро, хорошо оптимизированы и позволяют обходиться вообще без вызова системных функций. Все функции самодостаточные и не требуют для работы каких-либо дополнительных данных.
Читать статью целиком »
Просмотров: 8724 | Комментариев: 4
Преобразование вещественного числа в строку на Ассемблере
14.03.2014 | Категория: Образ мышления: Assembler | Автор: ManHunter
Ранее я выкладывал статью о том, как на Ассемблере перевести строку в вещественное число, теперь настало время произвести обратную операцию, то есть перевести вещественное число в строку. В отличие от целых чисел, где достаточно нескольких строк кода, с преобразованием вещественных чисел пришлось повозиться. В результате появилась следующая функция. За основу взята аналогичная функция из пакета MASM, но со значительными доработками.Code (Assembler) : Убрать нумерацию
- ;------------------------------------------------------------
- ; Функция перевода вещественного числа в строку
- ;------------------------------------------------------------
- ; Портирование с MASM, доработка и оптимизация - ManHunter
- ; Параметры:
- ; lpFloat - указатель на вещественное число TBYTE
- ; lpResult - указатель на строку-приемник результата
- ;------------------------------------------------------------
- proc FloatToString lpFloat:DWORD, lpResult:DWORD
- ; Локальные переменные
- local digits_count:DWORD
- local tmp:DWORD
- local old_cw:WORD
- local new_cw:WORD
- local saved_float:TBYTE
- local tmp1 rb 12h
- local tmp2 rb 12h
- ; Сохранить все регистры
- pusha
- ; Указатель на строку-приемник
- mov edi,[lpResult]
- ; Это ноль?
- mov esi,[lpFloat]
- cmp dword [esi],0
- jne loc_not_zero
- cmp dword [esi+4],0
- jne loc_not_zero
- cmp word [esi+8],0x8000
- je loc_minus_zero
- cmp word [esi+8],0
- jne loc_not_zero
- ; Записать в строку ноль
- mov al,'0'
- stosb
- jmp loc_ret
- loc_minus_zero:
- ; Записать в строку минус ноль
- mov ax,'-0'
- stosw
- jmp loc_ret
- loc_not_zero:
- ; Denormalized?
- mov ax,word [esi+8]
- and ax,7F80h
- or ax,ax
- jnz loc_not_denorm
- cmp dword [esi],0
- jne loc_denorm
- cmp dword [esi+4],0
- je loc_not_denorm
- loc_denorm:
- mov esi,szDen
- movsd
- movsd
- movsd
- jmp loc_ret
- loc_not_denorm:
- ; Infinity или NaN?
- mov ax,word [esi+8]
- and ax,7F80h
- cmp ax,7F80h
- jne loc_not_inf_nan
- ; Это Infinity?
- cmp dword [esi],0
- jne loc_nan
- cmp dword [esi+4],80000000h
- jne loc_nan
- loc_infinity:
- mov esi,szInf
- movsd
- movsb
- loc_plus_minus:
- movsd
- mov esi,[lpFloat]
- test byte [esi+9],80h
- jz loc_ret
- mov esi,[lpResult]
- mov byte[esi],'-'
- jmp loc_ret
- loc_nan:
- mov esi,szNan
- jmp loc_plus_minus
- loc_not_inf_nan:
- ; Скопировать число в локальную переменную
- push edi
- mov esi,[lpFloat]
- lea edi,[saved_float]
- movsd
- movsd
- movsw
- pop edi
- ; Число отрицательное?
- cmp dword [saved_float+6],0
- jge loc_not_signed
- ; Привести число к абсолютному значению
- and byte [saved_float+9],7Fh
- ; Записать в строку минус
- mov al,'-'
- stosb
- loc_not_signed:
- ; Проверить число на наличие дробной части и
- ; подсчитать количество цифр в нем
- fclex
- ; Сохранить управляющее слово
- fstcw [old_cw]
- ; Установить управляющее слово
- mov [new_cw],0000001001111111b
- fldcw [new_cw]
- lea esi,[saved_float]
- fld tbyte [esi]
- fld st
- ; Выделить мантиссу и порядок
- fxtract
- fstp st
- fldlg2
- ; Получить количество цифр в числе
- fmulp st1,st
- fistp [digits_count]
- ; Если цифр больше 16, то число отображается в
- ; нормализованном виде с мантиссой и экспонентой
- cmp [digits_count],10h
- jnb loc_not_integer
- ; У числа есть дробная часть?
- fld st
- frndint
- fcomp st1
- fstsw ax
- test ah,01000000b
- ; Да, отображать число с дробной частью
- jz loc_not_integer
- ; Целое число без дробной части и экспоненты
- lea eax,[tmp1]
- fbstp [eax]
- ; Перевести BCD-число в строку
- push edi
- lea esi,[tmp1+8]
- lea edi,[tmp2]
- mov ecx, 9
- @@:
- std
- xor eax,eax
- lodsb
- cld
- rol ax,12
- rol ah,4
- add ax,'00'
- stosw
- loop @b
- pop edi
- ; Пропустить лидирующий ноль
- mov eax,11h
- mov ecx,[digits_count]
- sub eax,ecx
- inc ecx
- lea esi,[tmp2+eax]
- cmp byte [esi],'0'
- jne @f
- inc esi
- dec ecx
- @@:
- ; Перенести полученное число из временного буфера
- rep movsb
- jmp loc_clear_stack
- loc_not_integer:
- mov eax,10h
- sub eax,[digits_count]
- ; Преобразовать число в целое до 16 разрядов
- mov ecx,eax
- cmp eax,0
- jge @f
- neg eax
- @@:
- ; Для чисел больше 0 корректировка округления в сторону 0
- mov [new_cw],0000101001111111b
- cmp ecx,0
- jge @f
- mov [new_cw],0000011001111111b
- @@:
- ; Установить управляющее слово
- fldcw [new_cw]
- ; Возвести 10 в степень количества цифр
- mov [tmp],eax
- fild [tmp]
- fld [float2]
- fyl2x
- fld1
- fld st1
- fprem
- f2xm1
- faddp
- fscale
- ; Почистить стек
- fxch st1
- fstp st
- ; Если число меньше 0, то умножить, иначе разделить
- cmp ecx,0
- jge @f
- fdivp st1,st
- jmp loc_rounded
- @@:
- fmulp st1,st
- loc_rounded:
- ; Полученное значение меньше 1.0e16 ?
- fcom [float1]
- fstsw ax
- test ah,1
- jz @f
- fmul [float2]
- dec [digits_count]
- @@:
- ; Целое число без дробной части и экспоненты
- lea eax,[tmp1]
- fbstp [eax]
- ; Перевести BCD-число в строку
- push edi
- lea esi,[tmp1+8]
- lea edi,[tmp2]
- mov ecx, 9
- @@:
- std
- xor eax,eax
- lodsb
- cld
- rol ax,12
- rol ah,4
- add ax,'00'
- stosw
- loop @b
- pop edi
- ; Числу требуется мантисса и экспонента?
- lea esi,[tmp2+1]
- mov ecx,[digits_count]
- cmp ecx,-0Fh
- jl loc_mantiss_and_exponent
- cmp ecx,10h
- jg loc_mantiss_and_exponent
- ; Заполнить дробную часть числа
- inc ecx
- cmp ecx,0
- jg @f
- mov ax,'0.'
- stosw
- neg ecx
- mov al,'0'
- rep stosb
- mov ecx,10h
- jmp loc_fraction_filled
- @@:
- rep movsb
- mov al,'.'
- stosb
- mov ecx,10h
- sub ecx,[digits_count]
- loc_fraction_filled:
- rep movsb
- jmp @f
- loc_clear_fraction:
- ; Удалить завершающие нули дробной части
- dec edi
- @@:
- cmp byte [edi-1],'0'
- jz loc_clear_fraction
- cmp byte [edi-1],'.'
- jnz @f
- dec edi
- @@:
- jmp loc_clear_stack
- loc_mantiss_and_exponent:
- ; Дробная часть мантиссы
- movsb
- mov al,'.'
- stosb
- movsd
- movsd
- movsw
- ; Удалить завершающие нули дробной части
- @@:
- cmp byte [edi-1],'0'
- jne @f
- cmp byte [edi-2],'.'
- je @f
- dec edi
- jmp @b
- @@:
- ; Символ и знак экспоненты
- mov al,'e'
- stosb
- mov al,'+'
- mov ebx,[digits_count]
- cmp ebx, 0
- jge @f
- mov al,'-'
- neg ebx
- @@:
- stosb
- ; Значение экспоненты
- mov eax,ebx
- mov ecx,10
- mov ebx,4
- @@:
- dec ebx
- xor edx,edx
- div ecx
- add dl,'0'
- mov [tmp1+ebx],dl
- or ebx,ebx
- jnz @b
- ; Пропустить лидирующие нули экспоненты
- mov ecx,4
- lea esi,[tmp1]
- @@:
- lodsb
- cmp al,'0'
- jne @f
- dec ecx
- jmp @b
- @@:
- dec esi
- rep movsb
- loc_clear_stack:
- ; Восстановить управляющее слово
- fldcw [old_cw]
- loc_ret:
- ; Окончание строки
- mov al,0
- stosb
- ; Восстановить все регистры
- popa
- ret
- float1 dq 1.0e16
- float2 dq 10.0
- szInf db '+Infinity'
- szNan db '+NaN'
- szDen db 'Denormalized'
- endp
Читать статью целиком »
Просмотров: 11463 | Комментариев: 27