2 * sdl.hidd - SDL graphics/sound/keyboard for AROS hosted
3 * Copyright (c) 2007 Robert Norris. All rights reserved.
5 * This program is free software; you can redistribute it and/or modify it
6 * under the same terms as AROS itself.
9 #include <aros/symbolsets.h>
10 #include <aros/libcall.h>
12 #include <exec/types.h>
13 #include <exec/tasks.h>
14 #include <exec/lists.h>
15 #include <hardware/intbits.h>
16 #include <proto/exec.h>
17 #include <proto/graphics.h>
19 #include "sdl_intern.h"
21 #include LC_LIBDEFS_FILE
24 #include <aros/debug.h>
26 #define MAX_EVENTS (64)
28 AROS_UFH4(ULONG
, tick_handler
,
29 AROS_UFHA(ULONG
, dummy
, A0
),
30 AROS_UFHA(struct Task
, *task
, A1
),
31 AROS_UFHA(ULONG
, dummy2
, A5
),
32 AROS_UFHA(struct ExecBase
*, SysBase
, A6
)) {
35 Signal(task
, SIGBREAKF_CTRL_D
);
43 VOID
sdl_event_task(struct Task
*creator
, BYTE sync
, LIBBASETYPEPTR LIBBASE
) {
44 struct Interrupt tick_int
;
45 SDL_Event e
[MAX_EVENTS
];
48 D(bug("[sdl] event loop task starting up\n"));
50 tick_int
.is_Code
= (APTR
) &tick_handler
;
51 tick_int
.is_Data
= FindTask(NULL
);
52 tick_int
.is_Node
.ln_Name
= "SDL event tick";
53 tick_int
.is_Node
.ln_Pri
= 0;
54 tick_int
.is_Node
.ln_Type
= NT_INTERRUPT
;
55 AddIntServer(INTB_TIMERTICK
, &tick_int
);
57 D(bug("[sdl] event loop task running, signalling creator\n"));
59 Signal(creator
, 1 << sync
);
61 D(bug("[sdl] entering loop\n"));
64 Wait(SIGBREAKF_CTRL_D
);
67 if ((nevents
= S(SDL_PeepEvents
, e
, MAX_EVENTS
, SDL_GETEVENT
, SDL_MOUSEEVENTMASK
| SDL_KEYEVENTMASK
)) > 0) {
68 D(bug("[sdl] %d events pending\n", nevents
));
70 for (i
= 0; i
< nevents
; i
++) {
73 case SDL_MOUSEBUTTONDOWN
:
74 case SDL_MOUSEBUTTONUP
:
75 D(bug("[sdl] got mouse event, sending to mouse hidd\n"));
77 ObtainSemaphoreShared(&LIBBASE
->lock
);
78 if (LIBBASE
->mousehidd
)
79 Hidd_SDLMouse_HandleEvent(LIBBASE
->mousehidd
, &e
[i
]);
80 ReleaseSemaphore(&LIBBASE
->lock
);
86 D(bug("[sdl] got keyboard event, sending to keyboard hidd\n"));
88 ObtainSemaphoreShared(&LIBBASE
->lock
);
90 Hidd_SDLMouse_HandleEvent(LIBBASE
->kbdhidd
, &e
[i
]);
91 ReleaseSemaphore(&LIBBASE
->lock
);
100 static int sdl_event_init(LIBBASETYPEPTR LIBBASE
) {
105 D(bug("[sdl] creating event loop task\n"));
107 if ((task
= AllocMem(sizeof(struct Task
), MEMF_PUBLIC
| MEMF_CLEAR
)) == NULL
) {
108 D(bug("[sdl] couldn't allocate task memory\n"));
112 if ((stack
= AllocMem(AROS_STACKSIZE
, MEMF_PUBLIC
)) == NULL
) {
113 D(bug("[sdl] couldn't allocate task stack memory\n"));
114 FreeMem(task
, sizeof(struct Task
));
118 task
->tc_Node
.ln_Type
= NT_TASK
;
119 task
->tc_Node
.ln_Name
= "sdl.hidd event task";
120 task
->tc_Node
.ln_Pri
= 50;
122 NEWLIST(&task
->tc_MemEntry
);
124 task
->tc_SPLower
= stack
;
125 task
->tc_SPUpper
= (UBYTE
*) stack
+ AROS_STACKSIZE
;
127 #if AROS_STACK_GROWS_DOWNWARDS
128 task
->tc_SPReg
= (UBYTE
*) task
->tc_SPUpper
- SP_OFFSET
;
130 task
->tc_SPReg
= (UBYTE
*) task
->tc_SPLower
+ SP_OFFSET
;
133 sync
= SIGBREAKF_CTRL_C
;
135 if (NewAddTask(task
, sdl_event_task
, NULL
, TAGLIST(TASKTAG_ARG1
, FindTask(NULL
),
137 TASKTAG_ARG3
, LIBBASE
)) == NULL
) {
138 D(bug("[sdl] new task creation failed\n"));
139 FreeMem(stack
, AROS_STACKSIZE
);
140 FreeMem(task
, sizeof(struct Task
));
144 D(bug("[sdl] task created, waiting for it to start up\n"));
148 D(bug("[sdl] event loop task up and running\n"));
150 LIBBASE
->eventtask
= task
;
153 static int sdl_event_expunge(LIBBASETYPEPTR LIBBASE
) {
154 if (LIBBASE
->eventtask
== NULL
)
157 RemTask(LIBBASE
->eventtask
);
158 LIBBASE
->eventtask
= NULL
;
161 ADD2INITLIB(sdl_event_init
, 1)
162 ADD2EXPUNGELIB(sdl_event_expunge
, 1)