Look at this:

invoke SendMessage,,WM_GETTEXT,edx,text
invoke MessageBox,NULL,text,text,MB_OK

That works fine, and displays everything in edithwnd.

But if I do:



invoke SendMessage,,WM_GETTEXT,edx,text
stdcall strdelete,text,2,4
invoke MessageBox,NULL,text,text,MB_OK

This displays the text all wrong and weird. Why does this happen? tmp1 and text are both strings. It doesn't matter if I use stdcall or ccall (cdecl call).

This is the proc for strdelete:

proc strdelete, buf,pos1,pos2
enter
push ebx eax
invoke lstrlen,
mov ebx,eax
add ,0
invoke lstrcpyn,tmp1,,
mov eax, ; eax = pos1
add eax, ; eax += pos2
sub eax,1
add ,eax
invoke lstrcpyn,tmp2,,tmp1
invoke lstrcat,tmp1,tmp2
pop ebx eax
mov eax,tmp1
return
Posted on 2003-03-01 12:39:48 by CyberGuy
invoke lstrcpyn,tmp2,,tmp1


First of all I don't know how the push and pop macros work but it looks like the eax and ebx registers are popped in the same order they were pushed.

I think the line above might be your problem. I believe tmp1 is the address of a string buffer but the third paramter to the lstrcpyn function is the number of character to copy.
Posted on 2003-03-01 18:14:40 by Odyssey
Thanks, but now I have another problem.
My strcopy proc works perfectly except if I do something like this , it would mess up the text string variable.

invoke SendMessage,,WM_GETTEXTLENGTH,0,0
add eax,1
invoke SendMessage,,WM_GETTEXT,eax,text
stdcall strcopy,text,1,3
invoke MessageBox,NULL,text,"Text",MB_OK

Why does it mess up the text string variable? Now the message box only shows only one character in the edithwnd textbox. When I don't use my strcopy proc, it shows all of the text in edithwnd.



My strcopy proc is:
tmp1 is a string.

proc strcopy, buff,pos1,pos2 ; strcopy,"Hello",2,3 returns "ell"
enter
push eax
mov eax,
sub eax,1
add ,eax
mov eax,
add eax,1
invoke lstrcpyn,tmp1,,eax
pop eax
mov eax,tmp1
return
Posted on 2003-03-07 16:00:46 by CyberGuy
add ,eax


This is the only line that modifies the string. It adds to the value in buff the value in eax.
Posted on 2003-03-07 17:53:40 by Odyssey
But thats the only way to move the string address by somenumber of bytes, right? I mean I couldn't do invoke lstrcpy,strbuffer,somstring+eax,somenumberofbytes it only works with constant values.
Posted on 2003-03-08 11:50:03 by CyberGuy
Instead of using the buff you could use a register maybe something like

proc strcopy, buff,pos1,pos2 ; strcopy,"Hello",2,3 returns "ell"
enter
push eax
push esi
mov eax,
mov esi,
sub eax,1
add esi,eax
mov eax,
add eax,1
invoke lstrcpyn,tmp1,esi,eax
pop esi
pop eax
mov eax,tmp1
return
Posted on 2003-03-08 14:49:30 by Odyssey
I tried it , but for some reason the same thing happens, I don't know why though .

I know its in the proc because this doesn't work

invoke SendMessage,,WM_GETTEXTLENGTH,0,0
add eax,1
invoke SendMessage,,WM_GETTEXT,eax,text
stdcall strcopy,text,1,3
invoke MessageBox,NULL,text,"Text",MB_OK

and this does work

invoke SendMessage,,WM_GETTEXTLENGTH,0,0
add eax,1
invoke SendMessage,,WM_GETTEXT,eax,text
invoke lstrcat,text,"Hello"
invoke MessageBox,NULL,text,"Text",MB_OK
Posted on 2003-03-10 19:52:49 by CyberGuy
A few things:

1) Pos2 appears to be a length parameter, not a position parameter.

2) You are not terminating the copied string with a zero byte. Adding one to the length adds one more character, which might not be a zero byte.
Posted on 2003-03-10 20:35:54 by tenkey
I don't understand. I thought that the problem was that the string you passed to the function was being modified. But I tried your orginal code and the string was not modified.
Posted on 2003-03-10 20:55:01 by Odyssey
Thats what I don't understand, why doesn't it work when I use WM_GETTEXT , and I tried to null terminate it with 0 but it didn't work, plus I was display the text variable, not the variable returned by strcopy, I don't understand why it doesn't work in this situtation.
Posted on 2003-03-14 14:15:17 by CyberGuy
I am confused about what the strcopy is supposed to do. More specifically about the pos1 and pos1 parameters. Is the function supposed to extract the characters between pos1 and pos2 or does it copy pos2 characters starting at index pos1 in the string.
Posted on 2003-03-14 19:00:35 by Odyssey
Strcopy works like this strcopy,string,startpos,count
Count meaning the number of characters to the left to be copied. Like
strcopy,"Hello",4,2 ;returns "lo" (the 4th position, 2 characters)
Posted on 2003-03-16 13:02:33 by CyberGuy
I can't figure out why the function is not working. Maybe you could send a an example program where the function is not working.
Posted on 2003-03-17 06:05:23 by Odyssey
Ok, I modified the minipad example to show you the problem:


; Simple text editor - fasm example program

include '%include%\win32ax.inc'
IDM_SHOW = 101
IDM_EXIT = 102
IDM_ABOUT = 901
.data
_class db 'MINIPAD32',0
_edit db 'EDIT',0
_title db 'MiniPad',0
_about_title db 'About MiniPad',0
_about_text db 'This is Win32 example program created with flat assembler.',0
hinstance dd ?
edithwnd dd ?
editfont dd ?
msg MSG
wc WNDCLASS
client RECT
buffer db "",0
tmp1 db "",0
.code

proc strcopy, buff,pos1,pos2 ; strcopy,"Hello",2,3 returns "ell"
enter
push eax
mov eax,
sub eax,1
add ,eax
mov eax,
add eax,1
invoke lstrcpyn,tmp1,,eax
pop eax
mov eax,tmp1
return

start:

invoke GetModuleHandle,0
mov ,eax
invoke LoadIcon,eax,17
mov ,eax
invoke LoadCursor,0,IDC_ARROW
mov ,eax
mov ,0
mov ,WindowProc
mov ,0
mov ,0
mov eax,
mov ,eax
mov ,COLOR_WINDOW+1
mov ,0
mov ,_class
invoke RegisterClass,wc

invoke LoadMenu,,37
invoke CreateWindowEx,0,_class,_title,WS_VISIBLE+WS_OVERLAPPEDWINDOW,144,128,256,256,NULL,eax,,NULL

msg_loop:
invoke GetMessage,msg,NULL,0,0
or eax,eax
jz end_loop
invoke TranslateMessage,msg
invoke DispatchMessage,msg

jmp msg_loop

end_loop:
invoke ExitProcess,

proc WindowProc, hwnd,wmsg,wparam,lparam
enter
push ebx esi edi
cmp ,WM_CREATE
je wmcreate
cmp ,WM_SIZE
je wmsize
cmp ,WM_SETFOCUS
je wmsetfocus
cmp ,WM_COMMAND
je wmcommand
cmp ,WM_DESTROY
je wmdestroy
defwndproc:
invoke DefWindowProc,,,,
jmp finish
wmcreate:
invoke GetClientRect,,client
invoke CreateWindowEx,WS_EX_CLIENTEDGE,_edit,0,WS_VISIBLE+WS_CHILD+WS_HSCROLL+WS_VSCROLL+ES_AUTOHSCROLL+ES_AUTOVSCROLL+ES_MULTILINE,,,,,,0,,NULL
or eax,eax
jz failed
mov ,eax
invoke CreateFont,16,0,0,0,0,FALSE,FALSE,FALSE,ANSI_CHARSET,OUT_RASTER_PRECIS,CLIP_DEFAULT_PRECIS,DEFAULT_QUALITY,FIXED_PITCH+FF_DONTCARE,NULL
or eax,eax
jz failed
mov ,eax
invoke SendMessage,,WM_SETFONT,eax,FALSE
xor eax,eax
jmp finish
failed:
or eax,-1
jmp finish
wmsize:
invoke GetClientRect,,client
invoke MoveWindow,,,,,,TRUE
xor eax,eax
jmp finish
wmsetfocus:
invoke SetFocus,
xor eax,eax
jmp finish
wmcommand:
mov eax,
and eax,0FFFFh
cmp eax,IDM_SHOW
je show
cmp eax,IDM_ABOUT
je about
cmp eax,IDM_EXIT
je wmdestroy
jmp defwndproc
show:
invoke SendMessage,,WM_GETTEXTLENGTH,0,0
add eax,1
mov ebx,eax
invoke SendMessage,,WM_GETTEXT,ebx,buffer
mov byte ,0
invoke MessageBox,NULL,buffer,"Text in Edithwnd",MB_OK ;Works fine...
stdcall strcopy,buffer,1,3 ;First 3 characters
;This doesn't work, it displays buffer all wrong
invoke MessageBox,NULL,buffer,"Wrong text from edithwnd",MB_OK ;show what was in the edit box
jmp finish
about:
invoke MessageBox,,_about_text,_about_title,MB_OK
jmp finish
wmdestroy:
invoke DeleteObject,
invoke PostQuitMessage,0
xor eax,eax
finish:
pop edi esi ebx
return

section '.rsrc' resource data readable

; resource directory

directory RT_MENU,menus,\
RT_ICON,icons,\
RT_GROUP_ICON,group_icons,\
RT_VERSION,versions

; resource subdirectories

resource menus,\
37,LANG_ENGLISH+SUBLANG_DEFAULT,main_menu

resource icons,\
1,LANG_NEUTRAL,icon_data

resource group_icons,\
17,LANG_NEUTRAL,main_icon

resource versions,\
1,LANG_NEUTRAL,version_info

menu main_menu
menuitem '&File',0,MFR_POPUP
menuitem '&Show',IDM_SHOW,0
menuseparator
menuitem 'E&xit',IDM_EXIT,MFR_END
menuitem '&Help',0,MFR_POPUP + MFR_END
menuitem '&About...',IDM_ABOUT,MFR_END

icon main_icon,icon_data,'minipad.ico'

version version_info,VOS__WINDOWS32,VFT_APP,VFT2_UNKNOWN,LANG_ENGLISH+SUBLANG_DEFAULT,0,\
'FileDescription','MiniPad - example program',\
'LegalCopyright','No rights reserved.',\
'FileVersion','1.0',\
'ProductVersion','1.0',\
'OriginalFilename','MINIPAD.EXE'

.end start
Posted on 2003-03-17 14:45:11 by CyberGuy
I think I have found the problem. I replaced

buffer db "",0
tmp1 db "",0

with

buffer rb 250
tmp1 rb 250

and the program worked fine.

I don't know Fasm that well so I am not sure how buffer db "" works. Maybe some one more knowledgeable can help explain that.
Posted on 2003-03-17 15:30:41 by Odyssey
buffer db "",0 works exactly like just buffer db 0.
Posted on 2003-03-17 15:49:57 by Tomasz Grysztar
Thanks Privalov. I should have known.Strings are declared the same way with other assemblers. I was just wondering if it resized to fit any length string.
Posted on 2003-03-17 15:57:04 by Odyssey
Thanks :alright: :alright:
Posted on 2003-03-19 15:04:21 by CyberGuy
No problem
Posted on 2003-03-19 18:52:24 by Odyssey