forked from KolibriOS/kolibrios
uploaded @clip - global clipboard
git-svn-id: svn://kolibrios.org@895 a494cfbc-eb01-0410-851d-a64ba20cac60
This commit is contained in:
parent
929c2fa683
commit
7bc0071f59
413
programs/system/clip/trunk/@clip.ASM
Normal file
413
programs/system/clip/trunk/@clip.ASM
Normal file
@ -0,0 +1,413 @@
|
||||
; <--- description --->
|
||||
; compiler: FASM
|
||||
; name: Clipboard server/daemon
|
||||
; version: 0.2
|
||||
; author: barsuk
|
||||
|
||||
; <--- include all MeOS stuff --->
|
||||
include "lang.inc"
|
||||
include "..\..\..\MACROS.INC"
|
||||
|
||||
; <--- start of MenuetOS application --->
|
||||
MEOS_APP_START
|
||||
|
||||
;define DEBUG TRUE
|
||||
define DEBUG FALSE
|
||||
include "bdebug.inc"
|
||||
|
||||
DEFAULT_SIZE = 0x10010 ; 64K + size of headers
|
||||
MAX_SIZE = 0x01000000 ; 16 M
|
||||
MAX_FORMAT = 16
|
||||
DELAY = 10 ; 1/10 sec between sending attempts
|
||||
ATTEMPT = 5 ; number of sending attempts
|
||||
|
||||
|
||||
; <--- start of code --->
|
||||
CODE
|
||||
|
||||
; ¢®-¯¥à¢ëå, ¤® 㡨âì ¢á¥ @clip, ª ª¨¥ ©¤ãâáï:
|
||||
; ¤¥¬® ¡ãä¥à ®¡¬¥ ¤®«¦¥ ¡ëâì ⮫쪮 ®¤¨!
|
||||
; ¨ ¨¬ ®ª ¦¥âáï á ¬ë© ¬®«®¤®© ¨§ ¤¥¬®®¢...
|
||||
|
||||
mov ecx, 2 ; ¯¥à¢ë© ®¬¥à ᫮⠤«ï ¯à®¢¥àª¨
|
||||
mov ebp, info
|
||||
mov ebx, ebp
|
||||
mov edx, 18
|
||||
.next_process:
|
||||
mov eax, 9
|
||||
int 0x40
|
||||
cmp dword [ebx + 10], '@CLI'
|
||||
jnz .differ
|
||||
cmp byte [ebx + 14], 'P'
|
||||
jnz .differ
|
||||
.similar:
|
||||
xchg eax, edx
|
||||
mov ebx, 2
|
||||
int 0x40
|
||||
mov ebx, ebp
|
||||
xchg eax, edx
|
||||
.differ:
|
||||
inc ecx
|
||||
cmp ecx, eax
|
||||
jae .done ; process not found
|
||||
jmp .next_process
|
||||
|
||||
.done:
|
||||
mov eax, 68 ; init heap
|
||||
mov ebx, 11
|
||||
int 0x40
|
||||
|
||||
mov eax, 66 ; set hotkey: Ctrl-Alt-V
|
||||
mov ebx, 4
|
||||
mov ecx, 47
|
||||
mov edx, 0x110 ; 0x110
|
||||
int 0x40
|
||||
print "set hot key (1 bad)"
|
||||
pregs
|
||||
|
||||
mov ebp, DEFAULT_SIZE
|
||||
|
||||
mov eax, 68 ; get memory for buffer
|
||||
mov ebx, 12
|
||||
mov ecx, ebp
|
||||
int 0x40
|
||||
mov esi, IPC_buffer
|
||||
mov [esi], eax
|
||||
|
||||
mov eax, 60 ; define buffer for IPC
|
||||
mov ebx, 1
|
||||
mov ecx, [esi]
|
||||
mov edx, ebp
|
||||
int 0x40
|
||||
|
||||
mov eax, 40
|
||||
mov ebx, 01000010b ;
|
||||
int 0x40
|
||||
|
||||
wait_event: ; main cycle
|
||||
mov eax, [IPC_buffer]
|
||||
mov dword [eax], 0 ; unlock buffer
|
||||
mov dword [eax + 4], 8
|
||||
|
||||
mov eax, 10 ; wait
|
||||
int 0x40
|
||||
print "event"
|
||||
pregs
|
||||
|
||||
;dec eax
|
||||
;dec eax
|
||||
cmp eax, 2
|
||||
jnz ipc_event
|
||||
|
||||
print "hotkey"
|
||||
|
||||
mov eax, 2
|
||||
int 0x40
|
||||
pregs
|
||||
cmp ah, 47 ; "v" up
|
||||
jnz wait_event
|
||||
|
||||
print "hotkey v up"
|
||||
; it is hotkey
|
||||
mov eax, 1
|
||||
mov ebx, eax
|
||||
call find_format
|
||||
pregs
|
||||
cmp eax, -1
|
||||
jz wait_event
|
||||
mov esi, [data_buffer + eax * 4]
|
||||
mov edi, [data_size + eax * 4]
|
||||
mov ecx, 2
|
||||
print "ping"
|
||||
.next:
|
||||
mov eax, 72
|
||||
movzx edx, byte [esi]
|
||||
int 0x40 ; here we should pause if eax = 1
|
||||
pregs
|
||||
|
||||
inc esi
|
||||
dec edi
|
||||
jnz .next
|
||||
jmp wait_event
|
||||
|
||||
ipc_event:
|
||||
|
||||
; we get an IPC message
|
||||
|
||||
print "recv. "
|
||||
|
||||
mov eax, [IPC_buffer]
|
||||
mov dword [eax], 1 ; lock buffer
|
||||
mov dword [eax + 4], 8
|
||||
|
||||
dph1 dword [eax] ; lock
|
||||
dph1 dword [eax + 4] ; current used size
|
||||
dph1 dword [eax + 8] ; pid
|
||||
dph1 dword [eax + 12] ; len
|
||||
print ""
|
||||
dph1 dword [eax + 16] ; cmd << 16 | fmt
|
||||
dph1 dword [eax + 20]
|
||||
dph1 dword [eax + 24]
|
||||
|
||||
mov ebx, [eax + 8 + 4]
|
||||
cmp ebx, 8
|
||||
jb wait_event ; all my messages have 8-byte header
|
||||
; so ignore this one
|
||||
|
||||
movzx ecx, word [eax + 8 + 8] ; command
|
||||
cmp ecx, 1
|
||||
jz command_setsize
|
||||
cmp ecx, 2
|
||||
jz command_set
|
||||
cmp ecx, 3
|
||||
jz command_getsize
|
||||
cmp ecx, 4
|
||||
jz command_get
|
||||
cmp ecx, 5
|
||||
jz command_delete
|
||||
jmp wait_event ; unrecognised command
|
||||
|
||||
command_setsize:
|
||||
|
||||
; the only thing we really need to do here is to grow IPC buffer
|
||||
; no changes are done to real buffer of chosen format
|
||||
|
||||
; the bad thing is that IPC buffer grows and never becomes less.
|
||||
; i want to fix this in the next version.
|
||||
|
||||
print "set size"
|
||||
|
||||
mov esi, [IPC_buffer_size]
|
||||
mov ecx, [eax + 24] ; size
|
||||
add ecx, 0x18 ; for headers
|
||||
;pregs
|
||||
cmp esi, ecx
|
||||
jae wait_event
|
||||
print "ipc buffer resize from esi to ecx"
|
||||
pregs
|
||||
|
||||
mov ebp, MAX_SIZE ; sort of protection. forbid transfer of more
|
||||
cmp ecx, ebp ; than 16,7 Mb of data through buffer
|
||||
jbe not_much
|
||||
mov ecx, ebp
|
||||
|
||||
not_much:
|
||||
xchg eax, edi ; edx := [IPC_buffer]
|
||||
add ecx, 0x18 ; for headers
|
||||
|
||||
mov [IPC_buffer_size], ecx
|
||||
mov eax, 68
|
||||
mov ebx, 12
|
||||
int 0x40 ; get memory
|
||||
print "get mem for new buf, eax"
|
||||
pregs
|
||||
mov [IPC_buffer], eax
|
||||
|
||||
mov dword [eax + 4], 8
|
||||
mov edx, ecx
|
||||
mov ecx, eax
|
||||
mov eax, 60
|
||||
mov ebx, 1
|
||||
int 0x40 ; make it IPC buffer
|
||||
|
||||
mov ecx, edi
|
||||
mov eax, 68
|
||||
mov ebx, 13
|
||||
int 0x40 ; free old IPC buffer
|
||||
|
||||
jmp wait_event
|
||||
|
||||
command_set:
|
||||
print "set"
|
||||
|
||||
; here we put the data transfered to us to one of internal buffers
|
||||
|
||||
;;;outs eax + 0x18
|
||||
|
||||
movzx eax, word [eax + 18] ; format id
|
||||
call find_format
|
||||
cmp eax, -1
|
||||
jz new_format
|
||||
mov edx, eax
|
||||
|
||||
; free old buffer of this format
|
||||
|
||||
mov ecx, [data_buffer + edx * 4]
|
||||
mov eax, 68
|
||||
mov ebx, 13
|
||||
int 0x40
|
||||
jmp set_buffer
|
||||
|
||||
new_format:
|
||||
mov eax, data_count ; allocate a buffer
|
||||
mov edx, [eax]
|
||||
inc dword [eax] ; no protection, no checks. very bad :(
|
||||
set_buffer:
|
||||
mov eax, [IPC_buffer]
|
||||
mov ecx, dword [eax + 12]
|
||||
sub ecx, 8 ; get length of data itself
|
||||
; subtract size of my headers
|
||||
;pregs
|
||||
mov [data_size + edx * 4], ecx ; save length of data
|
||||
|
||||
mov eax, 68
|
||||
mov ebx, 12
|
||||
int 0x40
|
||||
mov [data_buffer + edx * 4], eax
|
||||
|
||||
; copy data from IPC to new buffer
|
||||
mov esi, [IPC_buffer]
|
||||
mov ebp, esi
|
||||
add esi, 24 ; start of data
|
||||
mov edi, eax
|
||||
rep movsb ; oh, me knows that it's bad
|
||||
|
||||
mov eax, ebp
|
||||
movzx ecx, word [eax + 18] ; format id
|
||||
mov [data_format + edx * 4], ecx
|
||||
|
||||
; debug
|
||||
; print "set debug"
|
||||
; mov eax, [data_buffer + edx * 4]
|
||||
; mov ebx, [data_size + edx * 4]
|
||||
; mov ecx, [data_format + edx * 4]
|
||||
; pregs
|
||||
|
||||
jmp wait_event
|
||||
|
||||
command_delete:
|
||||
movzx eax, word [eax + 18] ; format id
|
||||
cmp eax, -1
|
||||
jz command_clear
|
||||
call find_format
|
||||
cmp eax, -1
|
||||
jz wait_event
|
||||
mov ecx, [data_buffer + eax * 4]
|
||||
mov [data_format + eax * 4], 0
|
||||
mov eax, 68
|
||||
mov ebx, 13
|
||||
int 0x40
|
||||
jmp wait_event
|
||||
|
||||
command_clear:
|
||||
mov eax, 68
|
||||
mov ebx, 13
|
||||
mov edx, data_buffer
|
||||
.next:
|
||||
mov ecx, [edx]
|
||||
jecxz .nofree
|
||||
int 0x40
|
||||
.nofree:
|
||||
mov [edx + data_size - data_buffer], 0
|
||||
add edx, 4
|
||||
cmp edx, data_format
|
||||
jnae .next
|
||||
jmp wait_event
|
||||
|
||||
command_getsize:
|
||||
|
||||
print "get size"
|
||||
|
||||
; we should send reply, containing size of data with chosen format id
|
||||
movzx eax, word [eax + 18] ; format id
|
||||
mov esi, 4
|
||||
call find_format
|
||||
;pregs
|
||||
cmp eax, -1
|
||||
jz zero_size
|
||||
|
||||
lea edx, [data_size + eax * 4]
|
||||
mov eax, [edx]
|
||||
jmp send_getsize
|
||||
zero_size:
|
||||
mov edx, dw_zero ; send 0 to indicate that the buffer is empty
|
||||
send_getsize:
|
||||
jmp send_msg
|
||||
|
||||
command_get:
|
||||
print "get"
|
||||
|
||||
; we need to send the data
|
||||
|
||||
; [:||||:]
|
||||
|
||||
movzx eax, word [eax + 18] ; format id
|
||||
call find_format
|
||||
cmp eax, -1
|
||||
jz wait_event
|
||||
mov edi, eax ; ¥ä¨£
|
||||
|
||||
mov edx, [data_buffer + edi * 4]
|
||||
mov esi, [data_size + edi * 4]
|
||||
;jmp send_msg
|
||||
|
||||
send_msg:
|
||||
|
||||
; for debugging
|
||||
; mov eax, 5
|
||||
; mov ebx, DELAY*5
|
||||
; int 0x40
|
||||
|
||||
mov ebp, ATTEMPT ; number of attempts to send
|
||||
mov eax, [IPC_buffer]
|
||||
mov ecx, [eax + 8] ; sender PID
|
||||
mov eax, 60
|
||||
mov ebx, 2
|
||||
int 0x40
|
||||
print "send data result eax"
|
||||
pregs
|
||||
cmp eax, 2
|
||||
jz .wait
|
||||
cmp eax, 3 ; it is strange..
|
||||
jz .wait ; maybe he needs time to resize his buf
|
||||
jmp wait_event
|
||||
.wait:
|
||||
dec ebp
|
||||
jz wait_event
|
||||
mov eax, 5 ; sleep a bit
|
||||
mov ebx, DELAY
|
||||
int 0x40
|
||||
jmp send_msg
|
||||
|
||||
|
||||
find_format: ; small function returning number of format
|
||||
|
||||
;print "find format"
|
||||
push ebx
|
||||
mov ebx, eax ; format id
|
||||
and ebx, 0xffff ; it is word
|
||||
xor eax, eax
|
||||
next:
|
||||
cmp [data_format + eax * 4], ebx
|
||||
jz found
|
||||
inc eax
|
||||
cmp eax, MAX_FORMAT
|
||||
jb next
|
||||
not_found:
|
||||
or eax, -1
|
||||
found:
|
||||
;pregs
|
||||
pop ebx
|
||||
ret
|
||||
|
||||
; <--- initialised data --->
|
||||
DATA
|
||||
IPC_buffer dd 0
|
||||
IPC_buffer_size dd DEFAULT_SIZE ; initially 64K
|
||||
|
||||
info db 1024 dup(0) ; for process info
|
||||
|
||||
data_buffer dd MAX_FORMAT dup(0) ; buffer for some format
|
||||
; (256 formats max)
|
||||
data_format dd MAX_FORMAT dup(0) ; format id
|
||||
data_size dd MAX_FORMAT dup(0) ; size of buffer
|
||||
data_count dd 0 ; number of formats used
|
||||
dw_zero dd 0 ; used to tell that
|
||||
; we don't have a format
|
||||
|
||||
; <--- uninitialised data --->
|
||||
UDATA
|
||||
|
||||
|
||||
MEOS_APP_END
|
||||
; <--- end of MenuetOS application --->
|
47
programs/system/clip/trunk/bdebug.inc
Normal file
47
programs/system/clip/trunk/bdebug.inc
Normal file
@ -0,0 +1,47 @@
|
||||
; debugging include file by barsuk
|
||||
; if DEBUG=TRUE, adds debug.inc
|
||||
; if DEBUG=FALSE, adds stubs for several macros from debug.inc
|
||||
|
||||
match =TRUE, DEBUG
|
||||
{
|
||||
|
||||
include '..\..\..\debug.inc'
|
||||
|
||||
macro dph1 str
|
||||
\{
|
||||
debug_print_hex str
|
||||
push eax
|
||||
mov al, ' '
|
||||
call debug_outchar
|
||||
pop eax
|
||||
\}
|
||||
|
||||
macro outs str
|
||||
\{
|
||||
pushad
|
||||
lea edx, [str]
|
||||
call debug_outstr
|
||||
popad
|
||||
\}
|
||||
}
|
||||
|
||||
match =FALSE, DEBUG
|
||||
{
|
||||
|
||||
macro print message
|
||||
\{
|
||||
\}
|
||||
|
||||
macro pregs
|
||||
\{
|
||||
\}
|
||||
|
||||
macro dph1 str
|
||||
\{
|
||||
\}
|
||||
|
||||
macro outs str
|
||||
\{
|
||||
\}
|
||||
|
||||
}
|
7
programs/system/clip/trunk/build_ru.bat
Normal file
7
programs/system/clip/trunk/build_ru.bat
Normal file
@ -0,0 +1,7 @@
|
||||
@echo lang fix ru >lang.inc
|
||||
@fasm @clip.asm @clip
|
||||
@fasm cliptest.asm cliptest
|
||||
@fasm test2.asm test2
|
||||
@erase lang.inc
|
||||
@kpack @clip
|
||||
@rem pause
|
359
programs/system/clip/trunk/clip.inc
Normal file
359
programs/system/clip/trunk/clip.inc
Normal file
@ -0,0 +1,359 @@
|
||||
|
||||
; clipboard client module by barsuk.
|
||||
; version 0.2
|
||||
; see readme.txt
|
||||
|
||||
macro CLIP_BUFFER buf_name, buf_size
|
||||
{
|
||||
#buf_name:
|
||||
.size dd buf_size
|
||||
.sys1 dd ?
|
||||
.sys2 dd ?
|
||||
.data db buf_size dup(?)
|
||||
}
|
||||
|
||||
_ipc_send:
|
||||
; internally used routine
|
||||
; esi->buffer, edx = byte count
|
||||
|
||||
push ebx
|
||||
push ecx
|
||||
push ebp
|
||||
|
||||
mov ebp, ATTEMPT ; number of attempts to send
|
||||
xchg edx, esi
|
||||
.send_again:
|
||||
mov eax, 5
|
||||
mov ebx, SEND_DELAY
|
||||
int 0x40
|
||||
|
||||
mov eax, 60
|
||||
mov ebx, 2
|
||||
mov ecx, [clipboard_init.clipserv_pid]
|
||||
int 0x40
|
||||
print "send result eax"
|
||||
pregs
|
||||
|
||||
or eax, eax
|
||||
jz .ok
|
||||
cmp eax, 2
|
||||
jz .wait
|
||||
jmp .err
|
||||
.wait:
|
||||
dec ebp
|
||||
jz .err
|
||||
jmp .send_again
|
||||
.ok:
|
||||
mov eax, 1
|
||||
jmp .exit
|
||||
.err:
|
||||
xor eax, eax
|
||||
.exit:
|
||||
pop ebp
|
||||
pop ecx
|
||||
pop ebx
|
||||
xchg edx, esi
|
||||
ret
|
||||
|
||||
_ipc_recv:
|
||||
; used internally.
|
||||
; edx = default event mask of thread(!!!)
|
||||
; esi -> CLIP_buffer
|
||||
; result: eax == 1 - suc, 0 - err
|
||||
|
||||
push ebx
|
||||
push ecx
|
||||
|
||||
mov dword [esi + 4], 0 ; unlock buffer
|
||||
mov dword [esi + 8], 0 ;
|
||||
|
||||
push edx
|
||||
mov eax, 60 ; register buffer
|
||||
mov ebx, 1
|
||||
lea ecx, [esi + 4]
|
||||
mov edx, [esi]
|
||||
add edx, 8
|
||||
;print "register buffer"
|
||||
;pregs
|
||||
int 0x40
|
||||
pop edx
|
||||
|
||||
.wait:
|
||||
mov eax, 40 ; listen for IPC
|
||||
mov ebx, 01000000b
|
||||
int 0x40
|
||||
|
||||
mov eax, 23 ; wait for IPC event
|
||||
mov ebx, RECV_DELAY ; not too long
|
||||
int 0x40
|
||||
cmp eax, 7
|
||||
jnz .err
|
||||
|
||||
mov eax, [clipboard_init.clipserv_pid] ; not message from
|
||||
cmp eax, [esi + 4] ; daemon, so ignore
|
||||
jnz .wait
|
||||
|
||||
mov dword [esi + 4], 1 ; lock so it will not be spoiled
|
||||
|
||||
print "cli recv"
|
||||
dph1 [esi]
|
||||
dph1 [esi+4]
|
||||
dph1 [esi+8]
|
||||
dph1 [esi+12]
|
||||
dph1 [esi+16]
|
||||
dph1 [esi+20]
|
||||
print ""
|
||||
|
||||
mov eax, 40 ; restore event mask
|
||||
mov ebx, edx
|
||||
int 0x40
|
||||
mov eax, 1
|
||||
jmp .exit
|
||||
.err:
|
||||
xor eax, eax
|
||||
.exit:
|
||||
pop ecx
|
||||
pop ebx
|
||||
ret
|
||||
|
||||
|
||||
clipboard_init:
|
||||
; action: define IPC buffer and find clipserv process
|
||||
; output: eax == 0 - error, eax == 1 - success
|
||||
|
||||
push ebx
|
||||
push ecx
|
||||
push edx
|
||||
|
||||
; mov eax, 60 ; define buffer for IPC
|
||||
; mov ebx, 1
|
||||
; mov ecx, .IPC_real_buffer
|
||||
; mov edx, IPC_buffer_size
|
||||
; int 0x40
|
||||
|
||||
;print "buffer defined"
|
||||
|
||||
; mov [.IPC_buffer], ecx
|
||||
|
||||
push ebp
|
||||
mov ebp, 1
|
||||
.next_process:
|
||||
mov eax, 9
|
||||
mov ebx, .process_info
|
||||
mov ecx, ebp
|
||||
int 0x40
|
||||
mov ecx, eax
|
||||
mov ebx, .process_info + 10
|
||||
mov eax, [ebx]
|
||||
cmp eax, '@CLI'
|
||||
jnz .differ
|
||||
mov al, [ebx + 4]
|
||||
cmp al, 'P'
|
||||
jnz .differ
|
||||
jmp .similar
|
||||
|
||||
; mov edx, .clipserv_name
|
||||
;.compare:
|
||||
; mov al, [edx]
|
||||
; cmp al, 0
|
||||
; jz .similar
|
||||
; cmp al, [ebx]
|
||||
; jnz .differ
|
||||
; inc edx
|
||||
; inc ebx
|
||||
; jmp .compare
|
||||
.differ:
|
||||
inc ebp
|
||||
cmp ebp, ecx
|
||||
jae .err ; process not found
|
||||
jmp .next_process
|
||||
.similar:
|
||||
;print "found server"
|
||||
mov eax, dword [.process_info + 30]
|
||||
mov [.clipserv_pid], eax
|
||||
|
||||
mov eax, 1
|
||||
jmp .exit
|
||||
.err:
|
||||
;print "no server"
|
||||
xor eax, eax
|
||||
.exit:
|
||||
pop ebp
|
||||
pop edx
|
||||
pop ecx
|
||||
pop ebx
|
||||
ret
|
||||
.clipserv_pid dd 0
|
||||
.process_info db 1024 dup(0)
|
||||
;;.clipserv_name db '@clip',0
|
||||
;.IPC_buffer dd .IPC_real_buffer ; sorry
|
||||
;.IPC_real_buffer db IPC_buffer_size dup(0)
|
||||
|
||||
clipboard_write:
|
||||
; action: put to clipboard data in format (ax) from buffer
|
||||
; input: esi -> CLIP_buffer, ax = format id
|
||||
; output: eax == 0 - error, eax == 1 - success
|
||||
|
||||
push ecx
|
||||
push edx
|
||||
push edi
|
||||
|
||||
mov edx, [esi] ; CLIP_buffer.size
|
||||
|
||||
push edx
|
||||
push esi
|
||||
mov [.msg_set_size + 2], ax
|
||||
mov word [esi + 4 + 2], ax ; format id to low word of sys1
|
||||
mov dword [.msg_set_size + 8], edx
|
||||
mov esi, .msg_set_size
|
||||
mov edx, 12
|
||||
call _ipc_send
|
||||
pop esi
|
||||
pop edx
|
||||
or eax, eax
|
||||
jz .err
|
||||
|
||||
mov word [esi + 4], 2 ; COMMAND_SET to high word of sys1
|
||||
add esi, 4 ; esi->buffer.sys1
|
||||
add edx, 8
|
||||
call _ipc_send
|
||||
sub esi, 4
|
||||
or eax, eax
|
||||
jz .err
|
||||
|
||||
mov eax, 1
|
||||
print "write success"
|
||||
jmp .exit
|
||||
.err:
|
||||
print "write failed"
|
||||
xor eax, eax
|
||||
.exit:
|
||||
pop edi
|
||||
pop edx
|
||||
pop ecx
|
||||
ret
|
||||
|
||||
.msg_set_size dw 1
|
||||
dw 1
|
||||
dd 0
|
||||
dd 0
|
||||
|
||||
clipboard_read:
|
||||
; esi -> CLIP_buffer, ax = format id
|
||||
; edx - ¬ ᪠ᮡë⨩ ¯® 㬮«ç ¨î
|
||||
; result: eax = 1 - success, 0 - general failure,
|
||||
; -1 - buffer too small
|
||||
; edx = size of data
|
||||
|
||||
push ebx
|
||||
push ecx
|
||||
push ebp
|
||||
push esi
|
||||
push edi
|
||||
|
||||
mov ebp, edx
|
||||
|
||||
; get size
|
||||
|
||||
mov edi, esi
|
||||
mov esi, .msg_get_size
|
||||
mov word [esi], 3
|
||||
mov [esi + 2], ax
|
||||
mov [.msg_get_buf + 2], ax
|
||||
mov edx, 8
|
||||
call _ipc_send
|
||||
or eax, eax
|
||||
jz .err
|
||||
|
||||
;;mov edx, DEFAULT_MASK
|
||||
mov edx, ebp
|
||||
mov esi, .buf_for_size
|
||||
mov dword [esi], 4
|
||||
call _ipc_recv
|
||||
or eax, eax
|
||||
jz .err
|
||||
|
||||
mov eax, [esi + 12] ; space we need
|
||||
mov edx, [edi] ; space we have
|
||||
print "read size eax"
|
||||
pregs
|
||||
mov ecx, eax
|
||||
cmp eax, edx
|
||||
ja .size
|
||||
or eax, eax
|
||||
jz .err
|
||||
mov ebx, eax
|
||||
|
||||
mov esi, .msg_get_buf
|
||||
mov word [esi], 4
|
||||
mov edx, 8
|
||||
call _ipc_send
|
||||
or eax, eax
|
||||
jz .err
|
||||
|
||||
;print "send fuck"
|
||||
|
||||
mov edx, ebp
|
||||
mov esi, edi
|
||||
call _ipc_recv
|
||||
or eax, eax
|
||||
jz .err
|
||||
|
||||
print "read get data"
|
||||
|
||||
mov edx, ebx
|
||||
mov eax, 1
|
||||
print "read ok"
|
||||
jmp .exit ; i'm an idiot. Never will I code at night again
|
||||
; i put jz instead of jmp.
|
||||
|
||||
.size:
|
||||
print "buffer small"
|
||||
mov edx, eax
|
||||
or eax, -1
|
||||
jmp .exit
|
||||
.err:
|
||||
print "read error"
|
||||
xor eax, eax
|
||||
.exit:
|
||||
pop edi
|
||||
pop esi
|
||||
pop ebp
|
||||
pop ecx
|
||||
pop ebx
|
||||
ret
|
||||
|
||||
.msg_get_size dw 0
|
||||
dw 1
|
||||
dd 0
|
||||
.msg_get_buf dw 0
|
||||
dw 1
|
||||
dd 0
|
||||
.buf_for_size dd 0
|
||||
dd 0
|
||||
dd 0
|
||||
dd 0
|
||||
|
||||
|
||||
clipboard_delete:
|
||||
; ax = format id to delete
|
||||
; result: eax = 0 error, = 1 ok
|
||||
|
||||
push edx
|
||||
push esi
|
||||
|
||||
mov esi, .msg_del
|
||||
mov word [esi], 5
|
||||
mov [esi + 2], ax
|
||||
mov edx, 8
|
||||
|
||||
call _ipc_send
|
||||
|
||||
pop esi
|
||||
pop edx
|
||||
|
||||
ret
|
||||
.msg_del dw 0
|
||||
dw 1
|
||||
dd 0
|
||||
|
168
programs/system/clip/trunk/clip.txt
Normal file
168
programs/system/clip/trunk/clip.txt
Normal file
@ -0,0 +1,168 @@
|
||||
Ž¡é¥á¨áâ¥¬ë© ¡ãä¥à ®¡¬¥ ¤«ï Ž‘ Š®«¨¡à¨.
|
||||
ˆä®à¬ æ¨ï ¤«ï à §à ¡®â稪®¢.
|
||||
|
||||
Šà ⪮: <20>ãä¥à ॠ«¨§®¢ ç¥à¥§ ¯à®æ¥áá-¤¥¬® ¨ IPC-á®®¡é¥¨ï.
|
||||
„«ï ¯à®¢¥àª¨ 㦮 § ¯ãáâ¨âì @clip(¤¥¬®) ¨
|
||||
(cliptest ¨ ¤®áªã ®â« ¤ª¨) ¨«¨ test2(¬®¦® ¥áª®«ìª®).
|
||||
|
||||
1. „¥¬® @clip ¨ ¥£® ª®¬ ¤ë.
|
||||
|
||||
„¥¬® @clip ॠ«¨§®¢ ª ª ¯à®æ¥áá, ¥ ᮧ¤ î騩 ®ª® (§ 祬 ®¨ ¥¬ã),
|
||||
⮫쪮 á«ãè î騩 IPC-á®®¡é¥¨ï. „¥¬® ¯®¤¤¥à¦¨¢ ¥â ¤® 16 (MAX_FORMAT) ¡ãä¥à®¢ ¤«ï
|
||||
à §«¨çëå ä®à¬ ⮢ ¤ ëå, ¨ ¤® 16,7 Œ¡ (MAX_SIZE) ¤ ëå ¢ ª ¦¤®¬ ¡ãä¥à¥
|
||||
(¯ ¬ïâì ®â¢®¤¨âáï ¤¨ ¬¨ç¥áª¨).
|
||||
Id ä®à¬ â ¤ ëå - ç¨á«® ®â 0 ¤® 65534 (§ 票¥ 65535 § १¥à¢¨à®¢ ®).
|
||||
|
||||
<EFBFBD>ਠ§ ¯ã᪥ ¤¥¬® § ¢¥àè ¥â ¢á¥ ¤à㣨¥ ¯à®æ¥ááë @clip.
|
||||
|
||||
Š®¬ ¤ë, ¯¥à¥¤ ¢ ¥¬ë¥ ¤¥¬®ã, ¨¬¥îâ ä®à¬ â:
|
||||
|
||||
[ Cmd: word | Format: word | Reserved: Dword | Data: ...]
|
||||
|
||||
£¤¥ Cmd - ª®¤ ª®¬ ¤ë,
|
||||
Format - id ä®à¬ â ¤ ëå,
|
||||
Reserved - ç⮠㣮¤® (¥ ¨á¯®«ì§ã¥âáï),
|
||||
¨ Data - ¤ ë¥, á¬ëá« ª®â®àëå § ¢¨á¨â ®â ª®¬ ¤ë.
|
||||
|
||||
„¥¬® ¢®á¯à¨¨¬ ¥â á«¥¤ãî騥 ª®¬ ¤ë:
|
||||
|
||||
Š®¤ 1. Set Size. “ª § âì ¥®¡å®¤¨¬ë© à §¬¥à ¡ãä¥à ¤«ï ¯à¨¥¬ ¤ ëå. <20>® í⮩
|
||||
ª®¬ ¤¥ ¤¥¬® ¯à¨ ¥®¡å®¤¨¬®á⨠à áè¨àï¥â ᢮© ¡ãä¥à ¤«ï IPC-á®®¡é¥¨©
|
||||
(ᯮᮡ 㬥ìè¨âì ¡ãä¥à ¢ ⥪ã饩 ॠ«¨§ 樨 ¥â).
|
||||
<EFBFBD> à ¬¥âà Data: 1 Dword, ᮤ¥à¦ 騩 à §¬¥à ¤ ëå ¤«ï ¯¥à¥¤ ç¨.
|
||||
„«¨ ª®¬ ¤ë: 12 ¡ ©â.
|
||||
|
||||
Š®¤ 2. Set. <20>¥à¥¤ ç ¤ ëå. <20>® í⮩ ª®¬ ¤¥ ¤ ë¥ ª®¯¨àãîâáï ¢ ¯ ¬ïâì ¤¥¬® .
|
||||
<EFBFBD> à ¬¥âà Data: ¤ ë¥, ª®â®àë¥ ã¦® ᪮¯¨à®¢ âì.
|
||||
„«¨ ª®¬ ¤ë: 8 + (¤«¨ ¤ ëå) ¡ ©â.
|
||||
|
||||
Š®¤ 3. Get Size. <20>®«ãç¨âì à §¬¥à ¤ ëå, åà ïé¨åáï ¢ ¡ãä¥à¥ á 㪠§ ë¬ id
|
||||
ä®à¬ â . <20>® í⮩ ª®¬ ¤¥ ¤¥¬® ®â¯à ¢«ï¥â ®â¢¥â®¥ IPC-á®®¡é¥¨¥ ¤«¨®© 4
|
||||
¡ ©â , ᮤ¥à¦ 饥 à §¬¥à ¤ ëå ¢ ¡ãä¥à¥. …᫨ ¤ ë¥ ¢ ¡ãä¥à¥ ®âáãâáâ¢ãîâ,
|
||||
¢ á®®¡é¥¨¨ 㪠§ë¢ ¥âáï à §¬¥à 0.
|
||||
„«¨ ª®¬ ¤ë: 8 ¡ ©â.
|
||||
|
||||
Š®¤ 4. Get. <20>®«ãç¨âì ¤ ë¥ ¨§ ¡ãä¥à á 㪠§ ë¬ id ä®à¬ â . <20>® í⮩ ª®¬ ¤¥
|
||||
¤¥¬® ®â¯à ¢«ï¥â ®â¢¥â®¥ IPC-á®®¡é¥¨¥ 㦮© ¤«¨ë á ¤ 묨 ¨§ ¡ãä¥à .
|
||||
…᫨ ¤ ë¥ ¢ ¡ãä¥à¥ ®âáãâáâ¢ãîâ, ®â¢¥â®¥ á®®¡é¥¨¥ ¥ ®â¯à ¢«ï¥âáï.
|
||||
„«¨ ª®¬ ¤ë: 8 ¡ ©â.
|
||||
|
||||
Š®¤ 5. Delete. Žç¨áâ¨âì ¡ãä¥à á 㪠§ ë¬ id ä®à¬ â . …᫨ 㪠§ âì
|
||||
id ä®à¬ â = 0xFFFF, ¡ã¤ãâ ®ç¨é¥ë ¢á¥ ¡ãä¥àë.
|
||||
„«¨ ª®¬ ¤ë: 8 ¡ ©â.
|
||||
|
||||
ˆáå®¤ë© ä ©« - @clip.asm. …᫨ à ᪮¬¬¥â¨à®¢ âì áâà®çªã
|
||||
;define DEBUG TRUE
|
||||
¨ § ª®¬¬¥â¨à®¢ âì á«¥¤ãîéãî, â® ¤¥¬® ç¥â ¯¨á âì ¬®£® ¡ãª®¢®ª ¤®áªã
|
||||
®â« ¤ª¨, ¨ ¯® ¨¬ ¬®¦® ¡ã¤¥â çâ®-â® ¯®ïâì ® ¢®§¨ª îé¨å ®è¨¡ª å.
|
||||
DEFAULT_SIZE - ç «ìë© à §¬¥à IPC-¡ãä¥à
|
||||
MAX_SIZE - ®£à ¨ç¥¨¥ ¡ãä¥à
|
||||
MAX_FORMAT - ç¨á«® à §«¨çëå ä®à¬ ⮢, ª®â®àë¥ ¬®¦® § áããâì ¢ ¤¥¬®
|
||||
®¤®¢à¥¬¥® ( ¥á«¨ ¡®«ìè¥, ᣫîç¨â. ’®¦¥ ¤® ¯®ä¨ªá¨âì).
|
||||
DELAY - § ¤¥à¦ª ¬¥¦¤ã ¯®¯ë⪠¬¨ ®â¯à ¢ª¨ á®®¡é¥¨ï, /100 ᥪ.
|
||||
ATTEMPT - ª®«¨ç¥á⢮ ¯®¯ë⮪ ®â¯à ¢ª¨ á®®¡é¥¨ï § ï⮬㠨«¨ ¥ £®â®¢®¬ã
|
||||
¯à®æ¥ááã.
|
||||
|
||||
|
||||
2. clip.inc - ¡®à äãªæ¨© ¤«ï ¡®«¥¥ ¢ë᮪®ã஢¥£® ®¡é¥¨ï á ¤¥¬®®¬ @clip.
|
||||
<EFBFBD>¥ «¨§®¢ ® ç⥨¥ ¡ãä¥à ¨ § ¯¨áì ¢ ¡ãä¥à.
|
||||
|
||||
<EFBFBD>ਬ¥à ¨á¯®«ì§®¢ ¨ï - cliptest.asm (¢ë¢®¤ ¤®áªã ®â« ¤ª¨) ¨
|
||||
test2.asm.
|
||||
|
||||
<EFBFBD>ਠ¨á¯®«ì§®¢ ¨¨ clip.inc ¥®¡å®¤¨¬® 㪠§ âì á«¥¤ãî騥 § 票ï (ç¨á« ,
|
||||
¥áâ¥á⢥®, ¬®£ãâ ¡ëâì ¤à㣨¥):
|
||||
DEFAULT_MASK = 7 ; Œ ᪠ᮡë⨩ (á¬. äãªæ¨î 40) ¯® 㬮«ç ¨î ¤«ï
|
||||
; ⥪ã饣® ¯®â®ª . <20>㦠, çâ®¡ë ¯®á«¥ ¯à¨¥¬
|
||||
; IPC-á®®¡é¥¨ï (ª®£¤ ¬ ᪠¬¥ï¥âáï 01000000b)
|
||||
; ¢®ááâ ®¢¨âì áâ àãî ¬ áªã ( ¯®«ãç¨âì ¬ áªã •‡ ª ª).
|
||||
|
||||
SEND_DELAY = 10 ; ¯ 㧠¬¥¦¤ã ¯®¯ë⪠¬¨ ¯à¨ ®â¯à ¢ª¥ á®®¡é¥¨ï ¤¥¬®ã
|
||||
|
||||
RECV_DELAY = 100 ; ¢à¥¬ï ®¦¨¤ ¨ï ®â¢¥â ®â ¤¥¬® (¥á«¨ § íâ® ¢à¥¬ï
|
||||
; ¥ ¯à¨è¥« ®â¢¥â, â® ®è¨¡ª )
|
||||
; ¢à¥¬ï - ¢ á®âëå ᥪã¤ë (ª ª ¤«ï äãªæ¨¨ 5).
|
||||
|
||||
ATTEMPT = 5 ; ª®«¨ç¥á⢮ ¯®¯ë⮪ ®â¯à ¢ª¨ á®®¡é¥¨ï, ¥á«¨ ¤¥¬®
|
||||
; § ïâ
|
||||
|
||||
<EFBFBD>®á«¥ ¢ª«î票ï clip.inc áâ ®¢ïâáï ¤®áâã¯ë¬¨ äãªæ¨¨:
|
||||
|
||||
clipboard_init() - ¯®¨áª ¯à®æ¥áá @clip. <20>âã äãªæ¨î
|
||||
¬®¦® ¢ë§ë¢ âì ¬®£®ªà â® ( ¯à¨¬¥à, ¥á«¨ ¤¥¬® ¥ 襫áï ¨«¨ ¡ë«
|
||||
¯¥à¥§ ¯ãé¥), ® 1 à § ¢ë§¢ âì ®¡ï§ â¥«ì® ã¦®.
|
||||
‚®§¢à é ¥â 1 ¯à¨ ãá¯¥å¥ ¨ 0 ¯à¨ ¥ã¤ ç¥ (¥ ©¤¥ ¤¥¬®).
|
||||
|
||||
clipboard_write(esi 㪠§ë¢ ¥â ¡ãä¥à ¢ ä®à¬ ⥠CLIP_BUFFER (á¬. ¤ «¥¥),
|
||||
ax (á«®¢®) - id ä®à¬ â ) - § ¯¨áì ¤ ëå ¢ ¡ãä¥à ®¡¬¥ .
|
||||
‚믮«ï¥â ª®¬ ¤ë 1 ¨ 2. ‚®§¢à é ¥â 1 ¯à¨ ãá¯¥å¥ ¨ 0 ¯à¨ ¥ã¤ ç¥
|
||||
(¯à¨ç¨ë ¡ë¢ îâ à §ë¥: ¤¥¬® ¥ ¡ë« ©¤¥ ¨«¨ § ïâ ¨ â.¤.).
|
||||
|
||||
clipboard_read(esi 㪠§ë¢ ¥â ¡ãä¥à ¢ ä®à¬ ⥠CLIP_BUFFER (á¬. ¤ «¥¥),
|
||||
ax (á«®¢®) - id ä®à¬ â ) - ç⥨¥ ¤ ëå ¨§ ¡ãä¥à ®¡¬¥ . ‚믮«ï¥â
|
||||
ª®¬ ¤ë 3 ¨ 4. ‚®§¢à é ¥â ¢ eax 1 ¯à¨ ãᯥå¥, -1 ¯à¨ ¥å¢ ⪥ ¬¥áâ ¢
|
||||
¡ãä¥à¥-¯à¨¥¬¨ª¥(ª®â®àë© ¢ í⮬ á«ãç ¥ ¥ ¬¥ï¥âáï) ¨ 0 ¯à¨ ¯à®ç¨å ®è¨¡ª å.
|
||||
‚ edx(¯à¨ eax=1 ¨«¨ -1) ¢®§¢à é ¥âáï ¤¥©á⢨⥫ìë© à §¬¥à ¤ ëå ¢ ¡ãä¥à¥.
|
||||
|
||||
‡ ¬¥ç ¨¥. …᫨ ¯à¨«®¦¥¨¥ ¨á¯®«ì§ã¥â ¢å®¤ï騥 IPC ¥ ⮫쪮 ¤«ï à ¡®âë á
|
||||
¡ãä¥à®¬ ®¡¬¥ , á«¥¤ã¥â ®¡à ¡ âë¢ âì á®®¡é¥¨ï ¤¥¬® @clip ¢àãçãî, â.ª.
|
||||
¨ ç¥ ¬®¦¥â ¢®§¨ªãâì â ª ï á¨âã æ¨ï: á®®¡é¥¨¥ ®â ¤à㣮£® ¯à¨«®¦¥¨ï
|
||||
¯®¯ ¤¥â ¢ ¡ãä¥à í⮣® ¯à¨«®¦¥¨ï ¤«ï á®®¡é¥¨© ®â ¤¥¬® ¡ãä¥à ,
|
||||
¨ ¡ã¤¥â ¯à®¨£®à¨à®¢ ®.
|
||||
|
||||
’ ª¦¥ ¬®¦® ¨á¯®«ì§®¢ âì(¯®á«¥ ¢ë§®¢ clipboard_init) á«¥¤ãî騥 äãªæ¨¨ ¡®«¥¥
|
||||
¨§ª®£® ã஢ï:
|
||||
_ipc_send (esi 㪠§ë¢ ¥â ®¡ëçë© ¡ãä¥à, edx - ª®«¨ç¥á⢮ ¡ ©â).
|
||||
Žâ¯à ¢«ï¥â IPC-á®®¡é¥¨¥ ¤¥¬®ã. Žâ«¨ç¨¥ ®â äãªæ¨¨ 60/2 ¢ ⮬, çâ® _ipc_send
|
||||
¯®¢â®àï¥â ¥áª®«ìª® (â®ç¥¥, ATTEMPTS) à § ¯®¯ëâªã ®â¯à ¢ª¨, ¥á«¨ ¡ãä¥à ¤¥¬®
|
||||
§ ïâ (ª®¤ 2) ¨«¨ ¯¥à¥¯®«¥ (ª®¤ 3), á ¯ 㧮© ¢ SEND_DELAY/100 ᥪã¤.
|
||||
‚®§¢à é ¥â 1 ¯à¨ ãᯥå¥, 0 ¯à¨ ®è¨¡ª¥.
|
||||
|
||||
_ipc_recv(esi 㪠§ë¢ ¥â ¡ãä¥à ¢ ä®à¬ ⥠CLIP_BUFFER (á¬. ¤ «¥¥),
|
||||
edx = ¬ ᪠ᮡë⨩ ¯®â®ª ¯® 㬮«ç ¨î).
|
||||
†¤¥â á®®¡é¥¨ï ®â ¤¥¬® ¢ â¥ç¥¨¥ RECV_DELAY/100 ᥪã¤. <20>ਠãᯥå¥
|
||||
१ã«ìâ â á®åà ï¥âáï ¢ esi.
|
||||
‚®§¢à é ¥â 1 ¯à¨ ãᯥå¥, 0 ¯à¨ ®è¨¡ª¥.
|
||||
|
||||
”®à¬ â ¡ãä¥à ¤«ï à ¡®âë á ¡ãä¥à®¬ ®¡¬¥ :
|
||||
CLIP_BUFFER
|
||||
(+0) .size dd ? ; §¤¥áì ¤®«¦¥ ¡ëâì § ¯¨á à §¬¥à
|
||||
; ᮡá⢥® ¡ãä¥à (N)
|
||||
; ¯à¨ § ¯¨á¨ ¤ ëå ¢ ¡ãä¥à, ¥á«¨ 㦮
|
||||
; ®â¯à ¢¨âì ¬¥ì襥 ª®«¨ç¥á⢮ ¡ ©â,
|
||||
; ¢à¥¬¥® § ¯¨è¨â¥ íâ® ª®«¨ç¥á⢮ áî¤
|
||||
; (á¬. ¯à¨¬¥à test2)
|
||||
|
||||
(+4) .sys1 dd ? ; \ í⨠¯®«ï ¨á¯®«ì§ãîâáï ¬®¤ã«¥¬ clip.inc
|
||||
; - ¤«ï ¢ãâ२å 楫¥© ¨ ¥ ¤®«¦ë
|
||||
(+8) .sys2 dd ? ; / ¬®¤¨ä¨æ¨à®¢ âìáï ¯à¨«®¦¥¨¥¬
|
||||
|
||||
(+12) .data db N dup(?); ᮡá⢥® ¤ ë¥ ¡ãä¥à
|
||||
|
||||
“¤ ç¨ ¢ ¯à®£à ¬¬¨à®¢ ¨¨ ¨ ®â« ¤ª¥!
|
||||
|
||||
; barsuk, 21.08.2008
|
||||
|
||||
|
||||
|
||||
|
||||
@CLIP - ¤®¯®«¥¨¥. ‚¥àá¨ï 0.2.
|
||||
|
||||
<EFBFBD>¥ «¨§®¢ ¢®§¬®¦®áâì ¢áâ ¢ª¨ ⥪áâ ¢ ¯à¨«®¦¥¨ï, ¥ ¯®¤¤¥à¦¨¢ î騥 à ¡®âã
|
||||
á @clip, ¯à¨ ¯®¬®é¨ äãªæ¨¨ 72.1. Ž¤ ª®, ¨§-§ ®á®¡¥®á⥩ ॠ«¨§ 樨,
|
||||
¯à¨«®¦¥¨ï¬ ¯à¨å®¤¨â ª®¤ ¨§ edx, ¥§ ¢¨á¨¬® ®â ०¨¬ ¢¢®¤ (ascii/scancode).
|
||||
Ÿ à¥è¨«, çâ® ¡®«ìè¨á⢮ ¯à¨«®¦¥¨©, ¢á¥ ¦¥, î§ îâ ०¨¬ ascii, ¨ ¯®í⮬ã
|
||||
¢ë¡à « ¥£® ¨ ¤«ï @clip ( ⥠¯à¨«®¦¥¨ï, ª®â®àë¥ ¨á¯®«ì§ãîâ ०¨¬ ᪠-ª®¤®¢,
|
||||
¯®«ãç â ¥¢¥àë© ¢¢®¤).
|
||||
<EFBFBD>ë«® ¡ë ¥¯«®å® ¢¥á⨠¨§¬¥¥¨ï ¢ ï¤à® (å®âï ¡ë ¢®§¬®¦®áâì 㧠âì ç㦮©
|
||||
०¨¬ ¢¢®¤ ).
|
||||
|
||||
‚áâ ¢ª ®áãé¥á⢫ï¥âáï ¦ ⨥¬ £®àï祩 ª« ¢¨è¨ ctrl-alt-v. ‘ ç « 㦮
|
||||
§ ¯ãáâ¨âì ¯à¨«®¦¥¨¥, à ¡®â î饥 á @clip ( ¯à¨¬¥à, test2), ¨ ᪮¯¨à®¢ âì ¢
|
||||
¡ãä¥à á id = 1 (®¡ëçë© â¥ªáâ) ª ª®©-«¨¡® ⥪áâ.
|
||||
|
||||
…é¥ ¬ëá«ì: ¤®¡ ¢¨âì ¢ eolite ( å®à®è® ¡ë ¨ kfar) ª®¯¨à®¢ ¨¥ ¢ ¡ãä¥à
|
||||
⥪ã饣® ¯ã⨠¨ ¨¬¥¨ ä ©« ¯®¤ ªãàá®à®¬. Š®¬¯¨«ïæ¨ï ¢ fasm ¨ ᦠ⨥ ¢
|
||||
kpack áâ ¥â 㤮¡¥¥.
|
||||
|
||||
; 08.09.2008
|
141
programs/system/clip/trunk/clip_en.txt
Normal file
141
programs/system/clip/trunk/clip_en.txt
Normal file
@ -0,0 +1,141 @@
|
||||
Global clipboard for Kolibri. Notes for developers.
|
||||
|
||||
General info
|
||||
Clipboard is implemented using daemon process and IPC messages.
|
||||
To test, run @clip (the daemon process) and cliptest and debug board
|
||||
or test2 (several instances).
|
||||
|
||||
1. @clip daemon and its commands
|
||||
|
||||
Process @clip creates no windows, but only listens for IPC messages.
|
||||
Daemon supports 16 (MAX_FORMAT) buffers for different data types and up to
|
||||
16,7 Mb (MAX_SIZE) data in each buffer (memory is allocated from heap).
|
||||
Data format ID is a number from 0 to 65534. Value 65535 is reserved.
|
||||
|
||||
When the daemon is started it terminates all other @clip instances.
|
||||
Format of daemon's commands is following:
|
||||
|
||||
[ Cmd: word | Format: word | Reserved: Dword | Data: ...]
|
||||
|
||||
where Cmd is command id,
|
||||
Format is data format id,
|
||||
Reserved is unused (should be zero),
|
||||
and Data is command-specific data.
|
||||
|
||||
Following commands are implemented:
|
||||
|
||||
1. Set Size. Define required size for buffer. This command causes daemon to
|
||||
enlarge (if needed) its IPC buffer (there is currently no way to decrease
|
||||
size of the buffer).
|
||||
Data parameter: Dword with size of the data.
|
||||
Command length: 12 bytes.
|
||||
|
||||
2. Set. Data transfer. This command copies data to daemon's memory.
|
||||
Data parameter: data to be copied.
|
||||
Command length: 8 + (data size) bytes.
|
||||
|
||||
3. Get Size. Get size of data with specified format id. This command causes
|
||||
daemon to send in reply an IPC message telling the size of the data in the buffer.
|
||||
If the buffer contains no data, 0 is returned.
|
||||
Command length: 8 bytes.
|
||||
|
||||
4. Get. Get the data with specified format id from the buffer. This command
|
||||
causes daemon to send in reply an IPC message of required size with the data
|
||||
from the buffer. If the buffer contains no data, no message is sent.
|
||||
Command length: 8 bytes.
|
||||
|
||||
5. Delete. Clear the buffer for specified format id. If 0xFFFF is specified,
|
||||
all buffers are cleared.
|
||||
Command length: 8 bytes.
|
||||
|
||||
Source: @clip.asm. Uncomment the line:
|
||||
;define DEBUG TRUE
|
||||
and comment the next one to enable output on debug board. This is useful
|
||||
for bugtracking.
|
||||
DEFAULT_SIZE is initial IPC buffer size
|
||||
MAX_SIZE is upper limit of IPC buffer size
|
||||
MAX_FORMAT is number of formats daemon can store as the same time
|
||||
(if more formats are copied, daemon will crash).
|
||||
DELAY is pause between sending attepmts, 1/100 seconds.
|
||||
ATTEMPT is number of sending attempts if target process is not ready.
|
||||
|
||||
|
||||
2. clip.inc: function set for high-level communication with @clip.
|
||||
Reading and writing is implemeted.
|
||||
|
||||
Usage example: cliptest.asm (writes to debug board) and test2.asm.
|
||||
|
||||
Following values should be defined:
|
||||
DEFAULT_MASK = 7 ; Default event mask for current thread
|
||||
|
||||
SEND_DELAY = 10 ; pause between sending attempts
|
||||
|
||||
RECV_DELAY = 100 ; how much to wait for the answer
|
||||
; 1/100 secs
|
||||
|
||||
ATTEMPT = 5 ; number of sending attempts
|
||||
|
||||
Clip.inc contains the following functions:
|
||||
|
||||
clipboard_init() - search of process @clip. May be called several times.
|
||||
Returns 1 if successful and 0 if failed.
|
||||
|
||||
clipboard_write(esi points to CLIP_BUFFER,
|
||||
ax (word) - data format id) - copies data to buffer.
|
||||
Uses 1-th and 2-nd commands.
|
||||
Returns 1 if successful and 0 if failed.
|
||||
|
||||
clipboard_read(esi points to CLIP_BUFFER,
|
||||
ax (word) - data format id) - retrieves data from buffer.
|
||||
Uses 3-rd and 4-th commands.
|
||||
Returns 1 if successful, -1 if not enough data in receive buffer (which is
|
||||
left unchanged in this case) and 0 if failed.
|
||||
If eax = 1 or -1, edx contains real size of data in the buffer.
|
||||
|
||||
Warning. If the application uses incoming IPC messages for other
|
||||
purposes, process daemon's messages manually, because getting a different
|
||||
format message will be ignored by clipboard_read.
|
||||
|
||||
There are 2 low-level functions which may be called after clipboard_init:
|
||||
_ipc_send (esi points to a common buffer, edx - byte count).
|
||||
Sends an IPC message to daemon. The difference between this function and
|
||||
function 60/2 is that _ipc_send makes several attempts if daemon is
|
||||
unaccessible, with pause of SEND_DELAY/100 seconds.
|
||||
Returns 1 if successful and 0 if failed.
|
||||
|
||||
_ipc_recv(esi points to CLIP_BUFFER (á¬. ¤ «¥¥),
|
||||
edx = default event mask).
|
||||
Waits for an IPC message for RECV_DELAY/100 seconds.
|
||||
If successful, result is stored in esi.
|
||||
Returns 1 if successful and 0 if failed.
|
||||
|
||||
Format of buffer for clipboard:
|
||||
CLIP_BUFFER
|
||||
(+0) .size dd ? ; size of the buffer itself(N)
|
||||
; if you need to send less bytes that N
|
||||
; temporarily write the required size here
|
||||
|
||||
(+4) .sys1 dd ? ; \ clip.inc uses these fields
|
||||
; - for internal values. You should not
|
||||
(+8) .sys2 dd ? ; / modify them
|
||||
|
||||
(+12) .data db N dup(?); buffer itself
|
||||
|
||||
Good luck in programming and debugging!
|
||||
|
||||
; barsuk, 21.08.2008
|
||||
|
||||
|
||||
|
||||
|
||||
@CLIP version 0.2.
|
||||
|
||||
A capability of inserting text to applications not using @clip is added.
|
||||
Function 72/1 is used to insert the text.
|
||||
Only applications, using ascii mode for input are supported.
|
||||
|
||||
To insert text press ctrl-alt-v hot key.
|
||||
The text should be copied to 1-st buffer from @clip-compatible
|
||||
application (example: test2).
|
||||
|
||||
; 08.09.2008
|
240
programs/system/clip/trunk/cliptest.ASM
Normal file
240
programs/system/clip/trunk/cliptest.ASM
Normal file
@ -0,0 +1,240 @@
|
||||
; <--- description --->
|
||||
; compiler: FASM
|
||||
; name: Clipboard Client Demo
|
||||
; version: 0.1
|
||||
; author: barsuk
|
||||
|
||||
|
||||
; <--- include all MeOS stuff --->
|
||||
include "lang.inc"
|
||||
include "..\..\..\MACROS.INC"
|
||||
|
||||
TEST_SIZE = 100000 ; ¤®«¦® ¤¥«¨âìáï 4
|
||||
|
||||
IPC_buffer_size = TEST_SIZE + 0x10
|
||||
MAX_BUFFER = TEST_SIZE + 0x10
|
||||
|
||||
SEND_DELAY = 10
|
||||
RECV_DELAY = 100
|
||||
|
||||
ATTEMPT = 5 ; ç¨á«® ¯®¯ë⮪ ®â¯à ¢¨âì á®®¡é¥¨¥ ¤¥¬®ã, ¥á«¨
|
||||
; ® § ïâ
|
||||
|
||||
; <--- start of MenuetOS application --->
|
||||
MEOS_APP_START
|
||||
|
||||
define DEBUG TRUE
|
||||
include "bdebug.inc"
|
||||
|
||||
include "clip.inc"
|
||||
|
||||
; <--- start of code --->
|
||||
CODE
|
||||
|
||||
|
||||
;;; This is the entry point of the program
|
||||
|
||||
begin:
|
||||
|
||||
print "clipboard testing module loaded"
|
||||
|
||||
mov eax, 5
|
||||
mov ebx, 100 ; 5 sec
|
||||
int 0x40
|
||||
|
||||
call clipboard_init
|
||||
or eax, eax
|
||||
jz .err
|
||||
|
||||
; put the data into clip_buffer
|
||||
|
||||
mov esi, test_line
|
||||
mov edi, cb.data
|
||||
mov ecx, cb.size
|
||||
rep movsb
|
||||
|
||||
print "init ok. @clip found."
|
||||
|
||||
mov esi, cb
|
||||
mov eax, 2
|
||||
call clipboard_write
|
||||
or eax, eax
|
||||
jz .err
|
||||
|
||||
print "write test ok."
|
||||
|
||||
; á«¥£ª ®ç¨á⨬ ¡ãä¥à, ¤«ï ¤¥¦®á⨠¯à®¢¥àª¨
|
||||
|
||||
mov dword [cb.data], 0
|
||||
|
||||
;jmp .exit
|
||||
mov eax, 3 ; try to read bad data
|
||||
mov esi, cb
|
||||
mov edx, 7
|
||||
call clipboard_read
|
||||
or eax, eax
|
||||
jz .bad2
|
||||
cmp eax, -1
|
||||
jz .err
|
||||
|
||||
.bad2:
|
||||
print "unset data read ok 1."
|
||||
mov eax, 88 ; -"-
|
||||
mov esi, cb
|
||||
mov edx, 7
|
||||
call clipboard_read
|
||||
or eax, eax
|
||||
jz .bad3
|
||||
cmp eax, -1
|
||||
jz .err
|
||||
|
||||
.bad3:
|
||||
print "unset data read ok 2."
|
||||
|
||||
.read:
|
||||
mov eax, 2
|
||||
mov esi, cb
|
||||
mov edx, 7
|
||||
call clipboard_read ; read the string we've written
|
||||
or eax, eax
|
||||
jz .err
|
||||
cmp eax, -1
|
||||
jz .err
|
||||
|
||||
print "read ok o_O, data:"
|
||||
outs cb.data
|
||||
print ""
|
||||
|
||||
mov eax, 5
|
||||
mov ebx, 200
|
||||
int 0x40
|
||||
|
||||
|
||||
; ¯®á«¥¤ïï ¯à®¢¥àª - à¥á ©§ ¡ãä¥à . ¨¬¥®, ¢®§ì¬¥¬ ¬®£® ¤ ëå
|
||||
; ¨ ¯à®ª ç ¥¬ ¨å ç¥à¥§ ¡ãä¥à
|
||||
|
||||
mov eax, 68
|
||||
mov ebx, 11
|
||||
int 0x40
|
||||
|
||||
mov eax, 68
|
||||
mov ebx, 12
|
||||
mov ecx, TEST_SIZE + 12
|
||||
int 0x40
|
||||
mov [mega_buf], eax
|
||||
|
||||
mov dword [eax], TEST_SIZE
|
||||
|
||||
lea edx, [eax + 12]
|
||||
mov eax, 12131415
|
||||
shr ecx, 2
|
||||
.loop:
|
||||
mov [edx], eax
|
||||
add edx, 4
|
||||
dec ecx
|
||||
jnz .loop
|
||||
|
||||
print "mega buffer allocated and filled"
|
||||
|
||||
; now write it
|
||||
|
||||
mov esi, [mega_buf]
|
||||
mov eax, 69
|
||||
call clipboard_write
|
||||
or eax, eax
|
||||
jz .err
|
||||
|
||||
print "mega buffer written"
|
||||
mov eax, 5
|
||||
mov ebx, 100
|
||||
int 0x40
|
||||
|
||||
; clear it.
|
||||
|
||||
mov edx, [mega_buf]
|
||||
add edx, 12
|
||||
xor eax, eax
|
||||
mov ecx, TEST_SIZE/4
|
||||
.loopc:
|
||||
mov [edx], eax
|
||||
add edx, 4
|
||||
dec ecx
|
||||
jnz .loopc
|
||||
|
||||
; now read
|
||||
|
||||
mov eax, 69
|
||||
mov esi, [mega_buf]
|
||||
mov edx, 7
|
||||
call clipboard_read ; read the string we've written
|
||||
or eax, eax
|
||||
jz .err
|
||||
cmp eax, -1
|
||||
jz .err
|
||||
|
||||
print "mega buf read"
|
||||
|
||||
; now compare
|
||||
|
||||
mov edx, [mega_buf]
|
||||
add edx, 12
|
||||
mov eax, 12131415
|
||||
mov ecx, TEST_SIZE/4
|
||||
.loopm:
|
||||
cmp eax, [edx]
|
||||
jnz .err
|
||||
add edx, 4
|
||||
dec ecx
|
||||
jnz .loopm
|
||||
|
||||
print "deleting mega buf"
|
||||
|
||||
mov eax, 69
|
||||
call clipboard_delete
|
||||
or eax, eax
|
||||
jz .err
|
||||
|
||||
mov eax, 5
|
||||
mov ebx, 100
|
||||
int 0x40
|
||||
|
||||
print "if read error then all is ok"
|
||||
|
||||
mov eax, 69
|
||||
mov esi, [mega_buf]
|
||||
mov edx, 7
|
||||
call clipboard_read ; read the string we've written
|
||||
or eax, eax
|
||||
jz .reading
|
||||
jmp .err
|
||||
|
||||
.reading:
|
||||
|
||||
print "test complete!"
|
||||
|
||||
.exit:
|
||||
or eax, -1
|
||||
int 0x40
|
||||
|
||||
.err:
|
||||
print "error!"
|
||||
jmp .exit
|
||||
|
||||
|
||||
; <--- initialised data --->
|
||||
DATA
|
||||
|
||||
CLIP_BUFFER cb, 256
|
||||
|
||||
; in_buf db 256 dup(0)
|
||||
; out_buf db 'Cthulhu Fhtagn',0
|
||||
|
||||
test_line db 'Cthulhu Fhtagn',0
|
||||
mega_buf dd 0
|
||||
|
||||
; <--- uninitialised data --->
|
||||
UDATA
|
||||
|
||||
|
||||
MEOS_APP_END
|
||||
; <--- end of MenuetOS application --->
|
272
programs/system/clip/trunk/test2.asm
Normal file
272
programs/system/clip/trunk/test2.asm
Normal file
@ -0,0 +1,272 @@
|
||||
; <--- description --->
|
||||
; compiler: FASM
|
||||
; name: Clipboard test with GUI.
|
||||
; version: 0.1
|
||||
; author: barsuk
|
||||
; comments: uses edit_box by Maxxxx32,<Lrz> (old static version)
|
||||
|
||||
|
||||
; <--- include all MeOS stuff --->
|
||||
include "lang.inc"
|
||||
include "..\..\..\MACROS.INC"
|
||||
|
||||
; <--- start of MenuetOS application --->
|
||||
MEOS_APP_START
|
||||
|
||||
SEND_DELAY = 10
|
||||
RECV_DELAY = 100
|
||||
ATTEMPT = 5
|
||||
|
||||
|
||||
define DEBUG TRUE
|
||||
include "bdebug.inc"
|
||||
|
||||
include "editbox.inc"
|
||||
|
||||
include "clip.inc"
|
||||
|
||||
use_edit_box
|
||||
|
||||
; <--- start of code --->
|
||||
CODE
|
||||
|
||||
call clipboard_init
|
||||
|
||||
call draw_window ; at first create and draw the window
|
||||
|
||||
wait_event: ; main cycle
|
||||
|
||||
mov edi, input_box
|
||||
call edit_box.mouse
|
||||
|
||||
mov eax, 10
|
||||
int 0x40
|
||||
|
||||
cmp eax, 1 ; if event == 1
|
||||
je redraw ; jump to redraw handler
|
||||
cmp eax, 2 ; else if event == 2
|
||||
je key ; jump to key handler
|
||||
cmp eax, 3 ; else if event == 3
|
||||
je button ; jump to button handler
|
||||
|
||||
jmp wait_event ; else return to the start of main cycle
|
||||
|
||||
|
||||
redraw: ; redraw event handler
|
||||
call draw_window
|
||||
jmp wait_event
|
||||
|
||||
|
||||
key: ; key event handler
|
||||
mov eax, 2 ; get key code
|
||||
int 0x40
|
||||
|
||||
cmp ah, '0'
|
||||
jb no_digit
|
||||
cmp ah, '9'
|
||||
ja no_digit
|
||||
sub ah, '0'
|
||||
mov byte [format_id], ah
|
||||
call draw_window
|
||||
jmp wait_event
|
||||
no_digit:
|
||||
|
||||
mov edi, input_box
|
||||
call edit_box.key
|
||||
|
||||
jmp wait_event
|
||||
|
||||
|
||||
button: ; button event handler
|
||||
mov eax, 17 ; get button identifier
|
||||
int 0x40
|
||||
|
||||
cmp ah, 1
|
||||
jz exit
|
||||
|
||||
cmp ah, 5
|
||||
jz copy
|
||||
cmp ah, 6
|
||||
jz paste
|
||||
jmp wait_event
|
||||
copy:
|
||||
mov esi, input_text
|
||||
mov edi, buffer.data
|
||||
mov ecx, [buffer.size]
|
||||
rep movsb ; copy text to buffer
|
||||
|
||||
mov edi, input_box
|
||||
mov edx, [edi + 38] ; ed_size
|
||||
xchg edx, [buffer.size]
|
||||
movzx eax, byte [format_id]
|
||||
mov esi, buffer
|
||||
call clipboard_write
|
||||
xchg edx, [buffer.size]
|
||||
jmp wait_event
|
||||
|
||||
paste:
|
||||
mov esi, buffer
|
||||
movzx eax, byte [format_id]
|
||||
mov edx, 7
|
||||
call clipboard_read
|
||||
|
||||
or eax, eax
|
||||
jz wait_event
|
||||
|
||||
cmp eax, -1
|
||||
jz wait_event
|
||||
|
||||
or edx, edx
|
||||
jz wait_event ; íâ® ¢á¥ ®è¨¡ª¨
|
||||
|
||||
mov eax, input_box
|
||||
;print "input box"
|
||||
;dph1 [eax]
|
||||
;dph1 [eax+4]
|
||||
;dph1 [eax+8]
|
||||
;dph1 [eax+12]
|
||||
;dph1 [eax+16]
|
||||
;dph1 [eax+20]
|
||||
;dph1 [eax+24]
|
||||
|
||||
;;;;jmp wait_event
|
||||
|
||||
mov word [input_box + 36], ed_focus ; flags
|
||||
|
||||
mov ecx, [input_box + 38] ; size
|
||||
print "paste read ecx=size"
|
||||
jecxz .noloop
|
||||
mov edi, input_box
|
||||
mov ah, 8 ; backspace
|
||||
.loop:
|
||||
call edit_box.key
|
||||
dec ecx
|
||||
jnz .loop
|
||||
.noloop:
|
||||
mov esi, buffer.data
|
||||
mov ecx, edx
|
||||
pregs
|
||||
.loop2:
|
||||
mov ah, [esi]
|
||||
cmp ah, 0
|
||||
jz .done
|
||||
call edit_box.key ; ï ¡ë ᥡ¥ à㪨 ®â१ « § â ª®¥
|
||||
; ® çâ® ¤¥« âì, ¥á«¨ ¨ ç¥ ¥ ¯®«ãç ¥âáï?
|
||||
inc esi
|
||||
dec ecx
|
||||
jnz .loop2
|
||||
|
||||
.done:
|
||||
print "rest of data ecx"
|
||||
pregs
|
||||
call draw_window
|
||||
jmp wait_event
|
||||
|
||||
exit:
|
||||
or eax, -1 ; exit application
|
||||
int 0x40
|
||||
|
||||
|
||||
draw_window:
|
||||
mov eax, 12 ; start drawing
|
||||
mov ebx, 1
|
||||
int 0x40
|
||||
|
||||
mov eax, 0 ; create and draw the window
|
||||
mov ebx, 100*65536+400 ; (window_cx)*65536+(window_sx)
|
||||
mov ecx, 100*65536+250 ; (window_cy)*65536+(window_sy)
|
||||
mov edx, 0x33ffffff ; work area color & window type 3
|
||||
mov edi, head
|
||||
int 0x40
|
||||
|
||||
mov eax, 4
|
||||
mov ebx, 10 shl 16 + 10
|
||||
mov ecx, 0x80000000
|
||||
mov edx, text1
|
||||
int 0x40
|
||||
mov eax, 4
|
||||
mov ebx, 10 shl 16 + 20
|
||||
mov edx, text2
|
||||
int 0x40
|
||||
mov eax, 47
|
||||
mov ebx, 0x00020000
|
||||
movzx ecx, byte [format_id]
|
||||
mov edx, 200 shl 16 + 20
|
||||
mov esi, 0
|
||||
int 0x40
|
||||
|
||||
mov eax, 8
|
||||
mov ebx, 10 shl 16 + 60
|
||||
mov ecx, 40 shl 16 + 15
|
||||
mov edx, 5
|
||||
mov esi, 0xd72189
|
||||
int 0x40
|
||||
mov eax, 4
|
||||
mov ebx, 12 shl 16 + 42
|
||||
mov ecx, 0x80000000
|
||||
mov edx, button1
|
||||
int 0x40
|
||||
|
||||
mov eax, 8
|
||||
mov ebx, 80 shl 16 + 60
|
||||
mov ecx, 40 shl 16 + 15
|
||||
mov edx, 6
|
||||
mov esi, 0xd72189
|
||||
int 0x40
|
||||
mov eax, 4
|
||||
mov ebx, 82 shl 16 + 42
|
||||
mov ecx, 0x80000000
|
||||
mov edx, button2
|
||||
int 0x40
|
||||
|
||||
mov edi, input_box
|
||||
call edit_box.draw
|
||||
|
||||
; mov eax, 4
|
||||
; mov ebx, 10 shl 16 + 90
|
||||
; mov ecx, 0
|
||||
; mov edx, input_text
|
||||
; mov esi, [input_box + 38]
|
||||
; int 0x40
|
||||
; mov eax, esi
|
||||
;print "eax = edit etxt len"
|
||||
;pregs
|
||||
|
||||
|
||||
|
||||
mov eax, 12 ; finish drawing
|
||||
mov ebx, 2
|
||||
int 0x40
|
||||
|
||||
ret
|
||||
|
||||
|
||||
|
||||
; <--- initialised data --->
|
||||
DATA
|
||||
|
||||
format_id db 1
|
||||
|
||||
; buffer db 256 dup(0)
|
||||
|
||||
CLIP_BUFFER buffer, 256
|
||||
|
||||
input_text db 256 dup(0)
|
||||
input_box edit_box 100,10,70,0xffffff,0,0x00aaaaaa,0,255,input_text
|
||||
|
||||
; input_box edit_box 100,10,70,0xffffff,0,0xaaaaaa,0,\
|
||||
; 0xaaaaaa,0,255,input_text,ed_always_focus
|
||||
|
||||
head db "<22>ਬ¥à à ¡®âë á ¡ãä¥à®¬ ®¡¬¥ ",0
|
||||
text1 db "<22> ¦¨¬ ©â¥ æ¨äàë 0-9 ¤«ï ᬥë id ä®à¬ â ¤ ëå",0
|
||||
text2 db "‘¥©ç á ¢ë¡à id ä®à¬ â ¤ ëå: ",0
|
||||
|
||||
button1 db "Š®¯¨à®¢ âì",0
|
||||
button2 db "‚áâ ¢¨âì",0
|
||||
|
||||
; <--- uninitialised data --->
|
||||
UDATA
|
||||
|
||||
|
||||
MEOS_APP_END
|
||||
; <--- end of MenuetOS application --->
|
Loading…
Reference in New Issue
Block a user