From 2a493360e52fa6457f37c14ff439ed2a84f0d0cc Mon Sep 17 00:00:00 2001 From: hidnplayr Date: Sun, 9 Mar 2014 21:57:21 +0000 Subject: [PATCH] Small bugfixes and cleanup. git-svn-id: svn://kolibrios.org@4623 a494cfbc-eb01-0410-851d-a64ba20cac60 --- programs/network/ircc/gui.inc | 58 +++-- programs/network/ircc/ircc.asm | 53 +++-- programs/network/ircc/serverparser.inc | 318 ++++++++++++++----------- programs/network/ircc/socket.inc | 20 +- programs/network/ircc/textbox.inc | 102 ++++---- programs/network/ircc/userparser.inc | 68 +++--- programs/network/ircc/window.inc | 23 +- 7 files changed, 366 insertions(+), 276 deletions(-) diff --git a/programs/network/ircc/gui.inc b/programs/network/ircc/gui.inc index 9a679658e9..5daa0988e3 100644 --- a/programs/network/ircc/gui.inc +++ b/programs/network/ircc/gui.inc @@ -282,6 +282,23 @@ draw_windowtabs: cmp [edi + window.data_ptr], 0 jne .more_btn +; Draw the close window button + + mov edi, [window_active] + cmp [edi + window.type], WINDOWTYPE_SERVER ; dont let the user close server window + je @f + +; mov eax, 8 + mov ebx, [xsize] + sub ebx, 12 + shl ebx, 16 + mov bx, 12 + mov ecx, 6 shl 16 + 12 + mov edx, WINDOW_BTN_CLOSE + mov esi, 0x00aa0000 ; red ! + mcall + @@: + ; Draw the windownames onto the buttons mov eax, 4 @@ -305,25 +322,28 @@ draw_windowtabs: jnz .more .enough: -; Draw the close window button - - mov edi, [window_active] - cmp [edi + window.type], WINDOWTYPE_SERVER ; dont let the user close server window - je @f - - mov eax, 8 - mov ebx, [xsize] - sub ebx, 12 - shl ebx, 16 - mov bx, 12 - mov ecx, 6 shl 16 + 12 - mov edx, WINDOW_BTN_CLOSE -; mov esi, [colors.work_button] - mov esi, 0x00aa0000 ; red ! - mcall - - @@: - ret + +highlight_updated_tabs: + mov eax, 4 + mov ebx, 10 shl 16 + 15 + mov ecx, 0x80aa0000 + mov esi, MAX_WINDOWS + mov edi, windows + .more_: + test [edi + window.flags], FLAG_UPDATED + jz .next + lea edx, [edi + window.name] + mcall + .next: + add edi, sizeof.window ; get ptr to next window + cmp [edi + window.data_ptr], 0 + je .enough_ + add ebx, 125 shl 16 + dec esi + jnz .more_ + .enough_: + + ret \ No newline at end of file diff --git a/programs/network/ircc/ircc.asm b/programs/network/ircc/ircc.asm index a30e0b170f..e7eae9989c 100644 --- a/programs/network/ircc/ircc.asm +++ b/programs/network/ircc/ircc.asm @@ -13,7 +13,7 @@ ;; ;; ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; -version equ '0.19' +version equ '0.20' ; connection status STATUS_DISCONNECTED = 0 @@ -200,7 +200,7 @@ START: ; Welcome user mov esi, str_welcome - call print_text2 + call print_asciiz ; Check if parameter contains an URL cmp byte[param], 0 @@ -242,6 +242,7 @@ mainloop: jne .no_update call draw_channel_list .no_update: + call highlight_updated_tabs jmp mainloop @@ -290,8 +291,9 @@ button: mov ebx, [ebx + window.data_ptr] lea esi, [ebx + window_data.names + eax] call window_open - push [window_print] - pop [window_active] + test ebx, ebx + jz mainloop + mov [window_active], ebx call redraw jmp mainloop @@ -303,6 +305,11 @@ button: cmp ax, MAX_WINDOWS ja exit +; Save users scrollbar position + push [scroll1.position] + mov edx, [window_active] + pop [edx + window.users_scroll] + ; OK, time to switch to another window. mov dx, sizeof.window mul dx @@ -316,6 +323,9 @@ button: push [edx + window.text_line_print] pop [scroll2.position] + push [edx + window.users_scroll] + pop [scroll1.position] + call draw_window jmp mainloop @@ -436,7 +446,7 @@ ctcp_time db '] TIME', 10, 0 has_left_channel db ' has left ', 0 joins_channel db ' has joined ', 0 is_now_known_as db ' is now known as ', 0 -has_quit_irc db ' has quit IRC.', 10, 0 +has_quit_irc db ' has quit IRC', 10, 0 sets_mode db ' sets mode ', 0 str_kicked db ' is kicked from ', 0 @@ -445,7 +455,7 @@ str_nickchange db 'Nickname is now ', 0 str_realchange db 'Real name is now ', 0 str_talking db 'Now talking in ', 0 str_topic db 'Topic is "', 0 -str_topic_end db '".', 10, 0 +str_topic_end db '"', 10, 0 str_setby db 'Set by ', 0 str_connecting db 3, '3* Connecting to ', 0 @@ -456,17 +466,25 @@ str_disconnected db 3, '5* Server disconnected', 10, 0 str_reconnect db 3, '5* Connection reset by user', 10, 0 str_notconnected db 3, '5* Not connected to server', 10, 0 -str_dotnewline db '.',10, 0 -str_newline db 10, 0 str_1 db 3, '13 -', 0 str_2 db '- ', 0 -str_help db 10, 'following commands are available:', 10 +str_list db 'list', 0 + +str_help db 'The following commands are available:', 10 db 10 - db '/nick : change nickname to ', 10 - db '/real : change real name to ', 10 - db '/server
: connect to server
', 10 - db '/code : change codepage to cp866, cp1251, or utf8', 10, 0 + db '/nick : change nickname', 10 + db '/real : change real name', 10 + db '/server
: connect to server', 10 + db '/code : change codepage (cp866, cp1251, or utf8)', 10 + db '/join : join a channel', 10 + db '/part : part from a channel', 10 + db '/quit : quit server', 10 + db '/msg : send a private message', 10 + db '/ctcp : send a message using client to client protocol', 10 + db 10 + db 'Other commands are send straight to server.', 10 + db 10, 0 str_welcome db 3, '3 ___', 3, '7__________', 3, '6_________ ', 3, '4 __ __ __', 10 db 3, '3| \', 3, '7______ \', 3, '6_ ___ \ ', 3, '4 ____ | | |__| ____ _____/ |_', 10 @@ -583,11 +601,4 @@ quit_msg rb 250 windows rb MAX_WINDOWS*sizeof.window -IM_END: - - - - - - - +IM_END: \ No newline at end of file diff --git a/programs/network/ircc/serverparser.inc b/programs/network/ircc/serverparser.inc index 08b7653a9d..62a2e1d879 100644 --- a/programs/network/ircc/serverparser.inc +++ b/programs/network/ircc/serverparser.inc @@ -171,10 +171,12 @@ skip_parameter: cmd_justprint: add esi, 4 - call skip_parameter - call print_text2 - mov esi, str_newline - call print_text2 + call skip_parameter ; our nickname + + call print_asciiz + + mov al, 10 + call print_char ret @@ -191,22 +193,22 @@ cmd_notice: mov byte [esi-1], 0 push esi mov esi, str_1 - call print_text2 - mov eax, servercommand+1 - mov dl, '!' - call print_text + call print_asciiz + mov esi, servercommand+1 + mov bl, '!' + call print_string mov esi, str_2 - call print_text2 + call print_asciiz pop esi .gogogo: add esi, 6 call skip_parameter call skip_parameter - call print_text2 + call print_asciiz - mov esi, str_newline - call print_text2 + mov al, 10 + call print_char ret @@ -251,6 +253,8 @@ cmd_privmsg: push esi mov esi, servercommand+1 call window_open + test ebx, ebx + jz .fail2 pop esi call skip_parameter ; our own nickname @@ -261,6 +265,8 @@ cmd_privmsg: .channel: call window_open + test ebx, ebx + jz .fail .print: ; nope, just plain old privmsg, print it using ' message' format @@ -269,25 +275,29 @@ cmd_privmsg: end if push esi - mov bl, '<' - call print_character + mov al, '<' + call print_char - mov eax, servercommand+1 - mov dl, '!' - call print_text + mov esi, servercommand+1 + mov bl, '!' + call print_string - mov bl, '>' - call print_character + mov al, '>' + call print_char - mov bl, ' ' - call print_character + mov al, ' ' + call print_char pop esi - call print_text2 + call print_asciiz - mov bl, 10 - call print_character + mov al, 10 + call print_char + ret + + .fail2: + pop esi .fail: ret @@ -355,13 +365,13 @@ cmd_ctcp: end if mov esi, ctcp_header - call print_text2 + call print_asciiz mov esi, servercommand+1 - call print_text2 + call print_asciiz mov esi, ctcp_time - call print_text2 + call print_asciiz ret @@ -374,13 +384,13 @@ cmd_ctcp: end if mov esi, ctcp_header - call print_text2 + call print_asciiz mov esi, servercommand+1 - call print_text2 + call print_asciiz mov esi, ctcp_version - call print_text2 + call print_asciiz ret @@ -392,13 +402,13 @@ cmd_ctcp: end if mov esi, ctcp_header - call print_text2 + call print_asciiz mov esi, servercommand+1 - call print_text2 + call print_asciiz mov esi, ctcp_ping - call print_text2 + call print_asciiz ret @@ -411,20 +421,20 @@ cmd_ctcp: end if mov esi, action_header - call print_text2 + call print_asciiz - mov eax, servercommand+1 ; print nickname - mov dl, '!' - call print_text + mov esi, servercommand+1 ; print nickname + mov bl, '!' + call print_string - mov bl, ' ' - call print_character + mov al, ' ' + call print_char pop esi - call print_text2 ; print message + call print_asciiz - mov bl, 10 - call print_character + mov al, 10 + call print_char ret @@ -440,10 +450,13 @@ cmd_dcc: ret .send: - call window_open + test ebx, ebx + jz .fail mov [ebx + window.type], WINDOWTYPE_DCC + .fail: + ret @@ -520,27 +533,28 @@ cmd_part: .not_me: push esi call window_open + test ebx, ebx + jz .fail2 if TIMESTAMP call print_timestamp end if mov esi, part_header - call print_text2 + call print_asciiz - mov eax, servercommand+1 - mov dl, '!' - mov cl, ' ' - call print_text + mov esi, servercommand+1 + mov bl, '!' + call print_string mov esi, has_left_channel - call print_text2 + call print_asciiz pop esi - call print_text2 + call print_asciiz - mov esi, str_newline - call print_text2 + mov al, 10 + call print_char mov ebx, [window_print] mov esi, servercommand+1 @@ -548,6 +562,11 @@ cmd_part: ret + .fail2: + pop esi + + ret + cmd_join: @@ -556,14 +575,14 @@ cmd_join: jne .fail add esi, 5 ; skip 'JOIN ' -; compare nick: did we join a channel? +; did we join a channel? mov edi, servercommand+1 call compare_to_nick jne .not_me push esi call window_open - test eax, eax + test ebx, ebx jz .fail mov [ebx + window.type], WINDOWTYPE_CHANNEL mov [window_active], ebx @@ -573,17 +592,17 @@ cmd_join: end if mov esi, join_header - call print_text2 + call print_asciiz mov esi, str_talking - call print_text2 + call print_asciiz - pop eax - mov dl, ' ' - call print_text + pop esi + mov bl, ' ' + call print_string - mov esi, str_dotnewline - call print_text2 + mov al, 10 + call print_char call draw_window @@ -592,26 +611,28 @@ cmd_join: .not_me: push esi call window_open + test ebx, ebx + jz .fail if TIMESTAMP call print_timestamp end if mov esi, join_header - call print_text2 + call print_asciiz - mov eax, servercommand+1 - mov dl, '!' - call print_text + mov esi, servercommand+1 + mov bl, '!' + call print_string mov esi, joins_channel - call print_text2 + call print_asciiz pop esi - call print_text2 + call print_asciiz - mov esi, str_newline - call print_text2 + mov al, 10 + call print_char mov ebx, [window_print] mov esi, servercommand+1 @@ -620,7 +641,7 @@ cmd_join: ret .fail: - add esp, 4 + pop esi ret @@ -690,20 +711,20 @@ cmd_nick: end if mov esi, nick_header - call print_text2 + call print_asciiz - mov eax, servercommand+1 - mov dl, '!' - call print_text + mov esi, servercommand+1 + mov bl, '!' + call print_string mov esi, is_now_known_as - call print_text2 + call print_asciiz - mov esi, [esp + 8] ; FIXME: dont print the 0x0a0d!!! - call print_text2 + mov esi, [esp + 8] + call print_asciiz - mov esi, str_newline - call print_text2 + mov al, 10 + call print_char ; Now do this for all open windows .next_window: @@ -734,6 +755,8 @@ cmd_kick: ; find the channel user has been kicked from push esi call window_open + test ebx, ebx + jz .fail push esi if TIMESTAMP @@ -741,34 +764,37 @@ cmd_kick: end if mov esi, kick_header - call print_text2 + call print_asciiz - pop eax - mov dl, ' ' - call print_text + pop esi + mov bl, ' ' + call print_string mov esi, str_kicked - call print_text2 + call print_asciiz - pop eax - mov dl, ' ' - call print_text + pop esi + mov bl, ' ' + call print_string mov esi, str_by - call print_text2 + call print_asciiz - mov eax, servercommand+1 - mov dl, '!' - call print_text + mov esi, servercommand+1 + mov bl, '!' + call print_string - mov esi, str_dotnewline - call print_text2 + mov al, 10 + call print_char mov ebx, [window_print] mov esi, servercommand+1 call user_remove + ret + .fail: + pop esi ret @@ -800,14 +826,14 @@ cmd_quit: end if mov esi, quit_header - call print_text2 + call print_asciiz - mov eax, servercommand+1 - mov dl, '!' - call print_text + mov esi, servercommand+1 + mov bl, '!' + call print_string mov esi, has_quit_irc - call print_text2 + call print_asciiz ; TODO: check if quit message was given, and print it to the window pop ebx @@ -841,20 +867,20 @@ cmd_mode: end if mov esi, mode_header - call print_text2 + call print_asciiz - mov eax, servercommand+1 - mov dl, '!' - call print_text + mov esi, servercommand+1 + mov bl, '!' + call print_string mov esi, sets_mode - call print_text2 + call print_asciiz pop esi - call print_text2 + call print_asciiz - mov esi, str_newline - call print_text2 + mov al, 10 + call print_char ; TODO: keep track of user modes in username list @@ -868,21 +894,21 @@ cmd_mode: end if mov esi, mode_header - call print_text2 + call print_asciiz - mov eax, [esp] - mov dl, ' ' - call print_text + mov esi, [esp] + mov bl, ' ' + call print_string mov esi, sets_mode - call print_text2 + call print_asciiz pop esi call skip_parameter - call print_text2 + call print_asciiz - mov esi, str_newline - call print_text2 + mov al, 10 + call print_char ret @@ -894,6 +920,8 @@ cmd_353: ; channel usernames reply inc esi ; channel type '*', '=' or '@' inc esi ; ' ' call window_open + test ebx, ebx + jz .fail ; now find window ptr and check if this is the first 353 message mov ebx, [window_print] @@ -919,6 +947,7 @@ cmd_353: ; channel usernames reply .done: call draw_channel_list + .fail: ret @@ -931,9 +960,10 @@ cmd_366: ; channel usernames end add esi, 4 ; skip '366 ' call skip_parameter call window_open - - mov ebx, [window_print] + test ebx, ebx + jz .fail and [ebx + window.flags], not FLAG_RECEIVING_NAMES + .fail: ret @@ -945,6 +975,8 @@ cmd_topic: add esi, 4 ; skip '332 ' call skip_parameter call window_open + test ebx, ebx + jz .fail if TIMESTAMP call print_timestamp @@ -952,16 +984,18 @@ cmd_topic: push esi mov esi, topic_header - call print_text2 + call print_asciiz mov esi, str_topic - call print_text2 + call print_asciiz pop esi - call print_text2 + call print_asciiz mov esi, str_topic_end - call print_text2 + call print_asciiz + + .fail: ret @@ -971,6 +1005,8 @@ cmd_333: add esi, 4 ; skip '333 ' call skip_parameter call window_open + test ebx, ebx + jz .fail if TIMESTAMP call print_timestamp @@ -978,32 +1014,46 @@ cmd_333: push esi mov esi, topic_header - call print_text2 + call print_asciiz mov esi, str_setby - call print_text2 + call print_asciiz - pop eax - mov dl, '!' - call print_text + pop esi + mov bl, '!' + call print_string - mov esi, str_newline - call print_text2 + mov al, 10 + call print_char .fail: + ret + + cmd_322: ; LIST add esi, 4 - - mov [window_print], windows ; FIXME call skip_parameter - mov eax, esi - mov dl, 13 - call print_text - mov esi, str_newline - call print_text2 + + push esi + mov esi, str_list + call window_open + test ebx, ebx + jz .fail + + mov [window_active], ebx + call draw_windowtabs + pop esi + call print_asciiz + mov al, 10 + call print_char + + ret + + .fail: + pop esi ret diff --git a/programs/network/ircc/socket.inc b/programs/network/ircc/socket.inc index 4d69e16016..ac0d149104 100644 --- a/programs/network/ircc/socket.inc +++ b/programs/network/ircc/socket.inc @@ -21,11 +21,13 @@ socket_connect: call print_timestamp end if mov esi, str_connecting - call print_text2 + call print_asciiz + mov esi, irc_server_name - call print_text2 - mov esi, str_dotnewline - call print_text2 + call print_asciiz + + mov al, 10 + call print_char ; update status inc [status] ; was STATUS_DISCONNECTED, now STATUS_RESOLVING @@ -73,7 +75,7 @@ socket_connect: call print_timestamp end if mov esi, str_sockerr - call print_text2 + call print_asciiz ret @@ -84,7 +86,7 @@ socket_connect: call print_timestamp end if mov esi, str_dnserr - call print_text2 + call print_asciiz ret @@ -95,7 +97,7 @@ socket_connect: call print_timestamp end if mov esi, str_refused - call print_text2 + call print_asciiz ret @@ -104,7 +106,7 @@ socket_connect: call print_timestamp end if mov esi, str_reconnect - call print_text2 + call print_asciiz mov esi, quit_msg call cmd_usr_quit.with_message @@ -249,7 +251,7 @@ socket_receive: .disconnected: mov esi, str_disconnected - call print_text2 + call print_asciiz mov [status], STATUS_DISCONNECTED mcall close, [socketnum] diff --git a/programs/network/ircc/textbox.inc b/programs/network/ircc/textbox.inc index dbd2757a6a..79fcc898e1 100644 --- a/programs/network/ircc/textbox.inc +++ b/programs/network/ircc/textbox.inc @@ -52,9 +52,13 @@ text_insert_newlines: ; esi = ASCIIZ string ret +;---------------------------------- +; scan untill next line is reached +; ; When you set the direction flag before calling, you can also scan for previous line! -; in: esi -; out:esi +; IN: esi +; OUT: esi +;---------------------------------- text_nextline: mov ecx, [textbox_width] @@ -73,52 +77,65 @@ text_nextline: ret -print_text: ; eax = start ptr - ; dl = end char - pusha - ptr2: - mov bl, [eax] +;---------------------------------- +; print string +; +; IN: esi = ptr to string +; bl = char which marks end of string +; OUT: esi = ptr to end of str +;---------------------------------- +print_string: - cmp bl, dl + push eax + .loop: + lodsb + cmp al, bl je .done - test bl, bl + cmp al, 13 + je .loop + test al, al jz .done - call print_character - - inc eax - jmp ptr2 - + call print_char + jmp .loop .done: - popa + pop eax ret +;---------------------------------- +; print ASCIIZ string +; +; IN: esi = ptr to ASCIIZ string +; OUT: esi = ptr to end of str +;---------------------------------- +print_asciiz: -print_text2: ; esi = ptr to ASCIIZ string - - pusha + push eax .loop: lodsb test al, al jz .done - mov bl, al - call print_character + call print_char jmp .loop - .done: - popa + pop eax ret -print_character: +;---------------------------------- +; print character +; +; IN: al = char to print +; OUT: / +;---------------------------------- +print_char: push esi edi mov esi, [window_print] mov edi, [esi + window.text_write] - mov byte[edi], bl - inc edi + stosb cmp edi, [esi + window.text_end] jae .uh_ow mov [esi + window.text_write], edi @@ -330,33 +347,34 @@ print_timestamp: pusha mcall 3 ; get system time + mov ebx, eax - mov bl, '[' - call print_character + mov al, '[' + call print_char mov ecx, TIMESTAMP .loop: - mov bl, al - shr bl, 4 - add bl, '0' - call print_character + mov al, bl + shr al, 4 + add al, '0' + call print_char - mov bl, al - and bl, 0x0f - add bl, '0' - call print_character + mov al, bl + and al, 0x0f + add al, '0' + call print_char dec ecx jz .done - mov bl, ':' - call print_character - shr eax, 8 + mov al, ':' + call print_char + shr ebx, 8 jmp .loop .done: - mov bl, ']' - call print_character - mov bl, ' ' - call print_character + mov al, ']' + call print_char + mov al, ' ' + call print_char popa ret diff --git a/programs/network/ircc/userparser.inc b/programs/network/ircc/userparser.inc index 01f35f6469..cb24bff219 100644 --- a/programs/network/ircc/userparser.inc +++ b/programs/network/ircc/userparser.inc @@ -35,25 +35,25 @@ user_parser: call print_timestamp end if - mov bl, '<' - call print_character + mov al, '<' + call print_char mov esi, user_nick - call print_text2 + call print_asciiz - mov bl, '>' - call print_character - mov bl, ' ' - call print_character + mov al, '>' + call print_char + mov al, ' ' + call print_char mov eax, [edit1.size] mov byte[usercommand + eax],0 mov esi, usercommand - call print_text2 + call print_asciiz - mov bl, 10 - call print_character + mov al, 10 + call print_char ; and now send it to the server mov dword[packetbuf], 'PRIV' @@ -92,7 +92,7 @@ user_parser: .notconnected: mov esi, str_notconnected - call print_text2 + call print_asciiz ret @@ -145,7 +145,7 @@ server_command: .notconnected: mov esi, str_notconnected - call print_text2 + call print_asciiz ret @@ -200,20 +200,20 @@ cmd_usr_msg: end if mov esi, msg_header - call print_text2 - - mov eax, packetbuf+8 - mov dl, ' ' - call print_text - - mov bl, '*' - call print_character + call print_asciiz + mov esi, packetbuf+8 mov bl, ' ' - call print_character + call print_string + + mov al, '*' + call print_char + + mov al, ' ' + call print_char pop esi - call print_text2 + call print_asciiz .fail: ret @@ -313,11 +313,13 @@ cmd_usr_nick: stosb mov esi, str_nickchange - call print_text2 + call print_asciiz + mov esi, user_nick - call print_text2 - mov esi, str_dotnewline - call print_text2 + call print_asciiz + + mov al, 10 + call print_char ret @@ -343,11 +345,13 @@ cmd_usr_real: stosb mov esi, str_realchange - call print_text2 + call print_asciiz + mov esi, user_real_name - call print_text2 - mov esi, str_dotnewline - call print_text2 + call print_asciiz + + mov al, 10 + call print_char ret @@ -394,6 +398,8 @@ cmd_usr_quer: mov esi, usercommand+7 call window_open +; test ebx, ebx +; jz .fail ret @@ -402,7 +408,7 @@ cmd_usr_quer: cmd_usr_help: mov esi, str_help - call print_text2 + call print_asciiz ret diff --git a/programs/network/ircc/window.inc b/programs/network/ircc/window.inc index 5c011ec1db..9ac2940f84 100644 --- a/programs/network/ircc/window.inc +++ b/programs/network/ircc/window.inc @@ -82,25 +82,6 @@ window_set_name: ret - -window_is_updated: - - mov edi, [window_print] - cmp edi, [window_active] - je .skip - test [edi + window.flags], FLAG_UPDATED - jnz .skip - or [edi + window.flags], FLAG_UPDATED - -; TODO: make some noise - - call draw_windowtabs ; highlight updated tabs - .skip: - - ret - - - window_close: ; closes the 'print' window ; Remove the window (overwrite current structure with trailing ones) @@ -180,6 +161,7 @@ window_find: ; ; IN: esi = ptr to ASCIIZ windowname ; OUT: esi = ptr to next parameter +; ebx = window ptr/0 on error window_open: @@ -226,5 +208,6 @@ window_open: mov [window_print], ebx ret - .error: ; TODO: return error? + .error: + xor ebx, ebx ret \ No newline at end of file