flat assembler
Message board for the users of flat assembler.
![]() |
Author |
|
b1528932 07 Jul 2010, 23:43
mov r/m32,imm8
|
|||
![]() |
|
Tyler 07 Jul 2010, 23:46
Shift everything after the current offset 1 to the right, then insert the character. The shift could be done by starting at the end and moving blocks of 4. Make sure to access memory on aligned boundaries. I don't know if Windows uses it, but there's an exception for when memory is accessed unaligned.
|
|||
![]() |
|
Teehee 07 Jul 2010, 23:51
yep, i'm doing that, here my routine:
Code: .insertChar: cmp [cbi.textLength],0 ; if (len == 0 ) do not need to shift je .e mov edi,[cbi.textBase] ; fist address add edi,[cbi.textLength] ; go to last address mov esi,edi @@:dec esi ; esi = last - 1 mov bl, byte[esi] ; get char (in last - 1) mov byte[edi],bl ; put char (in last) dec edi ; dec last cmp esi,[cbi.textOffset] ; if (is not current offset) loop jne @b .e: inc [cbi.textLength] mov edi,[cbi.textOffset] ; current offset stosb ; insert inc [cbi.textOffset] but it seems too dumb. |
|||
![]() |
|
LocoDelAssembly 08 Jul 2010, 01:45
Code: .insertChar: ; textOffset <= textLength assumed mov ecx, [cbi.textLength] mov edi, [cbi.textOffset] sub ecx, edi add edi, [cbi.textBase] test ecx, ecx je .e @@: mov bl, [edi + ecx - 1] mov [edi + ecx], bl loop @b ; or dec ecx/jnz @b for possibly better execution speed .e: inc [cbi.textLength] stos byte [edi] inc [cbi.textOffset] Code: .insertChar: mov esi, [cbi.textLength] mov ecx, esi add esi, [cbi.textBase] lea edi, [esi + 1] sub ecx, [cbi.textOffset] std rep movs byte[edi], byte[esi] cld inc [cbi.textLength] stos byte [edi] inc [cbi.textOffset] [edit]Previously I wrongly assumed that the goal was to insert **always** at the beginning of the string. Now I corrected to make the code compatible to original Teehee's code (I hope). The second code, besides of being having the same problem it was not initializing ESI.[/edit] Last edited by LocoDelAssembly on 08 Jul 2010, 06:20; edited 1 time in total |
|||
![]() |
|
revolution 08 Jul 2010, 02:50
If your buffer is purely linear then you don't have any choice in the matter. You have to move as shown above. Either move the tail up or move the head down.
But if you are prepared to use a different buffer format then you have a myriad of options based upon what operations you need to perform on the buffer. I expect your question about inserting is just one of the operations you want to perform on the buffer. Perhaps best if you list for yourself all the operations you want to do and then choose a buffer format that would better suits the set of operations you are doing. |
|||
![]() |
|
edemko 08 Jul 2010, 05:30
That's redundant in our context:
Quote:
|
|||
![]() |
|
edemko 08 Jul 2010, 05:32
.insertChar can be called with char in AL: STOSB in enough then
|
|||
![]() |
|
LocoDelAssembly 08 Jul 2010, 06:28
I've fixed my code since I missed somehow what was the real goal (insert in any place of the text, not just the beginning). I haven't tested anything though so it could still be wrong.
edemko, I'm not sure what is redundant, you mean the "byte [edi]" part instead of using plain stosb? I did that for readability reasons (note that stosb and "stos byte[edi]" are both assembled as 0xAA so I'm not incurring in some performance penalty for the "extra" operand). |
|||
![]() |
|
edemko 08 Jul 2010, 09:27
quoted code can be skipped at all, i did not test it too
|
|||
![]() |
|
Teehee 08 Jul 2010, 12:34
@LocoDelAssembly: those codes tips are appreciated, thanks.
Revolution wrote: I expect your question about inserting is just one of the operations you want to perform on the buffer. Perhaps best if you list for yourself all the operations you want to do and then choose a buffer format that would better suits the set of operations you are doing. What do you mean by buffer format? if it will be linear or arrayed? in fact, im just trying to develop a code editor (like fasmw, just with some more features). So i need to build a all-text-functionalities component. @edemko: Code: inc [cbi.textOffset] ;;; What is this for? that update the offset to next position, so i insert there the next char. Or all chars will be put in the same position. |
|||
![]() |
|
edemko 08 Jul 2010, 13:47
Code: format pe gui 4.0 include 'win32ax.inc' rw equ readable writable section '' code executable import rw library kernel32,'kernel32.dll',\ user32,'user32.dll' include 'api\kernel32.inc' include 'api\user32.inc' buf db 255 dup 0 entry $ mov edi,buf stdcall loco_wide,edi,00,1,4 mov dword[edi],'CDEF' invoke MessageBoxA,0,edi,0,0 stdcall loco_wide,edi,04,1,4 mov dword[edi],'89AB' invoke MessageBoxA,0,edi,0,0 stdcall loco_wide,edi,08,1,4 mov dword[edi],'4567' invoke MessageBoxA,0,edi,0,0 stdcall loco_wide,edi,12,1,4 mov dword[edi],'0123' invoke MessageBoxA,0,edi,0,0 stdcall loco_wide,edi,16,2,4 mov dword[edi+1],'Loco' invoke MessageBoxA,0,edi,0,0 stdcall loco_wide,edi,20,7,3 mov word[edi+6],'De' mov byte[edi+8],'l' invoke MessageBoxA,0,edi,0,0 stdcall loco_wide,edi,23,11,8 mov dword[edi+10],'Asse' mov dword[edi+14],'mbly' invoke MessageBoxA,0,edi,0,0 ret proc loco_wide ;src(0..) ,lsrc(0..) ,start(1..) ,count(1..) enter 0,0 pushfd push edi mov edi,[ebp+20] sub edi,1 jc .edi ;count = 0 push esi mov esi,[ebp+16] sub esi,1 jc .esi ;start = 0 push ecx mov ecx,[ebp+12] cmp esi,ecx jae .ecx ;start > lsrc add edi,ecx ;lsrc + count -1 neg esi xadd ecx,esi ;edit: lsrc +1 dec esi ;edit: lsrc -1 add edi,[ebp+8] ;extend to src add esi,[ebp+8] ;extend ro src std ;optimize for... rep movsb ;...long buffers .ecx: pop ecx .esi: pop esi .edi: pop edi popfd leave ret 16 ;it seems so easy but took 1 hour! endp Last edited by edemko on 08 Jul 2010, 14:02; edited 1 time in total |
|||
![]() |
|
revolution 08 Jul 2010, 13:53
Teehee wrote: What do you mean by buffer format? if it will be linear or arrayed? If searching is a high priority then you can store the text in a simple word based database. If sorting is a high priority then you can store it in a line-indexed table. If insertion/deletion is a high priority then you can store it as partial fixed sized chunks (and index those also for some extra speed). If highlighting/colouring is a high priority then you can store it in a multi-byte layout, or as a shadowed buffer. Maybe even as a run length encoded meta data buffer. Lots of other choices also. Don't forget to use Google. ![]() Up to you what best suits your purpose. |
|||
![]() |
|
edfed 08 Jul 2010, 18:19
a choise for fast insertion is to provide modificators.
for exemple: Code: db 'string where text have to be inserted' if you want to edit text in a continuous way, just create a pointer to a new string. this pointer to identify the location where to insert the string. Code: db 'string where text have to be inserted' dd 10 db 'THE WORDS TO INSERT' after concatenation of the two strings, you will have the text Code: db 'string wheTHE WORDS TO INSERTre text have to be inserted' but combinaison of strings will be made only when an action validate the insertion, for exemple, move the cursor with arrows, clic anywhere else... loose the focus... it is a sort of linked list, but very different |
|||
![]() |
|
snify 14 Jul 2010, 01:10
That's my way of doing it
Code: format PE GUI 4.0 include 'c:\program files\fasm\include\win32a.inc' start: mov edx, STRING lea ebx, [edx+POSITION] ;; edx = beginning, ebx = end position @@: inc edx cmp byte [edx], 0 jne @b ;; edx = end of string @@: mov al, [edx] mov [edx+1], al dec edx cmp edx, ebx jne @b ;; loop backwards until it gets end pos mov byte [ebx+1], CHAR ;; replace the char invoke MessageBoxA,0,STRING,0,0 invoke ExitProcess,0 ;; test values POSITION = 3 CHAR = ' ' STRING db 'ABCDEFG',0,0,0 data import library kernel32,'KERNEL32.DLL',\ user32,'USER32.DLL' import kernel32,\ ExitProcess,'ExitProcess' import user32,\ MessageBoxA,'MessageBoxA' end data |
|||
![]() |
|
< Last Thread | Next Thread > |
Forum Rules:
|
Copyright © 1999-2025, Tomasz Grysztar. Also on GitHub, YouTube.
Website powered by rwasa.