void DisposeWindowFromThreadID(uint32_t tid) { for (int i = 0; i < captures.size(); i++) { if (captures[i]->ThreadID == tid) { captures.removeAt(i); i--; } } for (int i = 0; i < windows.size(); i++) { guiserver_window* w = windows[i]; if (w->ThreadID == tid) { if (prevWindow == w) prevWindow = NULL; if (activeWindow == w) { activeWindow = NULL; // ActivateWindow(NULL); } if (w->FormBufferHandle != 0) { w->Visible = false; DrawWindow(w); } windows.removeAt(i); MemoryMap::unmap(w->Handle); i--; } } if (activeWindow == NULL) ActivateWindow(GetFrontWindow()); }
guiserver_window* GetTargetWindow(int x, int y) { int size = captures.size(); if (size > 0) { return captures[size - 1]; } for (int i = windows.size() - 1; i >= 0; i--) { guiserver_window* w = windows[i]; if (w->Parent != 0 || (w->Flags & WINDOWFLAGS_TOPMOST) == 0) continue; if (IsInWindow(w, x, y)) return w; } for (int i = windows.size() - 1; i >= 0; i--) { guiserver_window* w = windows[i]; if (w->Parent != 0 || (w->Flags & WINDOWFLAGS_TOPMOST) != 0 || (w->Flags & WINDOWFLAGS_BOTTOMMOST) != 0) continue; if (IsInWindow(w, x, y)) return w; } for (int i = windows.size() - 1; i >= 0; i--) { guiserver_window* w = windows[i]; if (w->Parent != 0 || (w->Flags & WINDOWFLAGS_TOPMOST) != 0 || (w->Flags & WINDOWFLAGS_BOTTOMMOST) == 0) continue; if (IsInWindow(w, x, y)) return w; } return NULL; }
bool DisposeWindow(uint32_t handle) { if (prevWindow != NULL && prevWindow->Handle == handle) prevWindow = NULL; if (activeWindow != NULL && activeWindow->Handle == handle) ActivateWindow(NULL); int size_c = captures.size(); for (int i = 0; i < size_c; i++) { if (captures[i]->Handle == handle) { captures.removeAt(i); break; } } int size_w = windows.size(); for (int i = 0; i < size_w; i++) { guiserver_window* w = windows[i]; if (w->Handle == handle) { if (w->__internal2) DestructionEffect(w); windows.removeAt(i); MemoryMap::unmap(handle); if (activeWindow == NULL) ActivateWindow(GetFrontWindow()); return true; } } return false; }
static guiserver_window* GetFrontWindow() { for (int i = windows.size() - 1; i >= 0; i--) { guiserver_window* w = windows[i]; if (w->Parent == 0 && (w->Flags & WINDOWFLAGS_BOTTOMMOST) == 0) return w; } for (int i = windows.size() - 1; i >= 0; i--) { guiserver_window* w = windows[i]; if (w->Parent == 0 && (w->Flags & WINDOWFLAGS_BOTTOMMOST) != 0) return w; } return NULL; }
void Monitor::ParseConfig(CString content) { _A<CString> lines = content.split_lines(); FOREACH(CString, line, lines) { if (!line.startsWith("SERVER=")) continue; _A<CString> p = line.split("="); if (p.get_Length() < 2) continue; CString path = p[p.get_Length() - 1]; _A<CString> q = path.split("/"); CString name = q[q.get_Length() - 1]; this->paths.add(path); this->servers.add(name); } END_FOREACH alive = new bool[servers.size()]; return; }
FILE* __mlibc_filelist_get(void *p, int n) { HList<FILE*>* list; if( p == NULL ) p = __mlibc_filelist_initializer(p); list = (HList<FILE*>*)p; if( list->size() <= n ) return NULL; return list->get(n); }
guiserver_bitmap* GetBitmapPointer(uint32_t handle) { int size = bitmaps.size(); for (int i = 0; i < size; i++) { if (bitmaps[i]->Handle == handle) return bitmaps[i]; } return NULL; }
static void registerReceiver(uint32_t tid) { int size = receivers.size(); for (int i = 0; i < size; i++) { if (receivers[i] == tid) return; } receivers.add(tid); }
guiserver_window* GetWindowPointer(uint32_t handle) { int size = windows.size(); for (int i = 0; i < size; i++) { guiserver_window* w = windows[i]; if (w->Handle == handle) return w; } return NULL; }
static void unregisterReceiver(uint32_t tid) { int size = receivers.size(); for (int i = 0; i < size; i++) { if (receivers[i] != tid) continue; receivers.removeAt(i); return; } }
static PEData* GetPEData(const CString& path) { int size = cache.size(); for (int i = 0; i < size; i++) { PEData* pe = cache[i]; if (pe->Path == path) return pe; } return NULL; }
int __mlibc_filelist_remove_by_index(void *p, int n) { HList<FILE*>* list; if( p == NULL ) p = __mlibc_filelist_initializer(p); list = (HList<FILE*>*)p; if( list->size() <= n ) return 0; list->removeAt(n); return 1; }
int __mlibc_filelist_add(void *p, FILE* f) { HList<FILE*>* list; if( p == NULL ) p = __mlibc_filelist_initializer(p); list = (HList<FILE*>*)p; if( list->size() >= FOPEN_MAX ) return 0; list->add(f); return 1; }
static guiserver_window* GetChild(guiserver_window* parent, int x, int y) { x -= parent->X + parent->OffsetX; y -= parent->Y + parent->OffsetY; for (int i = windows.size() - 1; i >= 0; i--) { guiserver_window* w = windows[i]; if (w->Parent == parent->Handle && IsInWindow(w, x, y)) return GetChild(w, x, y); } return parent; }
void DisposeAllWindow() { for (int i = 0; i < windows.size(); i++) { guiserver_window* w = windows[i]; if (Message::sendReceive(NULL, w->ThreadID, MSG_GUISERVER_DISPOSEWINDOW) != M_OK) { printf("Error %s:%d\n", __FILE__, __LINE__); exit(-1); } syscall_kill_thread(w->ThreadID); } }
void sendToClients(MessageInfo* msg) { for (int i = clients_.size() - 1; i >= 0; i--) { if (Message::send(clients_[i], msg) != M_OK) { monapi_warn("send error to pid = %x", clients_[i]); uint32_t temp; clients_.removeAt(i, &temp); } } }
static void ProcessMouseInfo(MessageInfo* msg) { guiserver_window* top = GetTargetWindow(msg->arg1, msg->arg2); guiserver_window* target = top; if (target != NULL && target->Protocol == 1 && captures.size() == 0) { target = GetChild(target, msg->arg1, msg->arg2); } if (prevWindow != target) { if (prevWindow != NULL) { if (Message::send(prevWindow->ThreadID, MSG_GUISERVER_MOUSELEAVE, prevWindow->Handle) != M_OK) { monapi_warn("Error %s:%d\n", __FILE__, __LINE__); } } if (target != NULL) { if (Message::send(target->ThreadID, MSG_GUISERVER_MOUSEENTER, target->Handle) != M_OK) { monapi_warn("Error %s:%d\n", __FILE__, __LINE__); } } prevWindow = target; } if (prevButton < msg->arg3 && activeWindow != top) ActivateWindow(top); MessageInfo m = *msg; if (target != NULL) switch (target->Protocol) { case 1: m.arg1 = target->Handle; m.arg2 = MAKE_DWORD(msg->arg1, msg->arg2); if (prevButton == msg->arg3) { m.header = MSG_GUISERVER_MOUSEMOVE; } else if (prevButton < msg->arg3) { m.header = MSG_GUISERVER_MOUSEDOWN; m.arg3 = msg->arg3 - prevButton; } else { m.header = MSG_GUISERVER_MOUSEUP; m.arg3 = prevButton - msg->arg3; } break; } prevButton = msg->arg3; if (target != NULL && Message::send(target->ThreadID, &m) != M_OK) { DisposeWindowFromThreadID(target->ThreadID); } }
void DrawWindow(guiserver_window* w, int wx, int wy, int ww, int wh, bool draw_screen /*= true*/) { if (w == NULL || w->FormBufferHandle == 0) return; if (!w->__internal2) CreationEffect(w); DrawImage(screen_buffer, wallpaper, wx, wy, wx, wy, ww, wh); _R r(wx, wy, ww, wh); int size_w = windows.size(); for (int i = 0; i < size_w; i++) { guiserver_window* w = windows[i]; if (w->Parent != 0 || (w->Flags & WINDOWFLAGS_TOPMOST) != 0 || (w->Flags & WINDOWFLAGS_BOTTOMMOST) == 0) continue; DrawWindowInternal(w, r); } for (int i = 0; i < size_w; i++) { guiserver_window* w = windows[i]; if (w->Parent != 0 || (w->Flags & WINDOWFLAGS_TOPMOST) != 0 || (w->Flags & WINDOWFLAGS_BOTTOMMOST) != 0) continue; DrawWindowInternal(w, r); } for (int i = 0; i < size_w; i++) { guiserver_window* w = windows[i]; if (w->Parent != 0 || (w->Flags & WINDOWFLAGS_TOPMOST) == 0) continue; DrawWindowInternal(w, r); } int size_ov = overlaps.size(); for (int i = 0; i < size_ov; i++) { overlaps[i]->Draw(wx, wy, ww, wh); } if (!draw_screen) return; DrawScreen(wx, wy, ww, wh); }
bool DisposeBitmap(uint32_t handle) { int size = bitmaps.size(); for (int i = 0; i < size; i++) { if (bitmaps[i]->Handle == handle) { bitmaps.removeAt(i); MemoryMap::unmap(handle); return true; } } return false; }
void notifyProcessCreated(uint32_t tid, uint32_t parent, const CString& path) { int i = 0; while (i < receivers.size()) { if (Message::send(receivers[i], MSG_PROCESS_CREATED, tid, parent, 0, path) == M_OK) { i++; } else { _printf("%s: can not connect to %d\n", SVR, receivers[i]); removeProcessInfo(receivers[i]); receivers.removeAt(i); } } }
void notifyProcessTerminated(uint32_t tid, int status) { int i = 0; while (i < receivers.size()) { if (Message::send(receivers[i], MSG_PROCESS_TERMINATED, tid, status) == M_OK) { i++; } else { _printf("%s: can not connect to %d\n", SVR, receivers[i]); removeProcessInfo(receivers[i]); receivers.removeAt(i); } } }
void Monitor::CheckServers() { //char buf[256]; PsInfo info; for (int i = 0; i < servers.size(); i++) { alive[i] = false; } syscall_set_ps_dump(); while (syscall_read_ps_dump(&info) == 0) { CString name = info.name; for (int i = 0; i < servers.size(); i++) { if (servers.get(i) == name) { alive[i] = true; continue; } } } for (int i = 0; i < servers.size(); i++) { if (alive[i]) continue; if (!firstLoad && servers[i] == "OLDSHELL.EX5") continue; // sorry we can not use printf before process server starts. syscall_print("loading "); syscall_print((const char*)paths.get(i)); syscall_print("...."); // We need OutStream MessageInfo msg; if (servers[i] == "SCHEME.EX5") { uint32_t tid; uint32_t targetID = Message::lookupMainThread("SCREEN.EX5"); if (targetID == THREAD_UNKNOWN || Message::sendReceive(&msg, targetID, MSG_SCREEN_GET_STREAM_HANDLE)) { syscall_print("SCREEN.EX5 not found\n"); continue; } syscall_print(monapi_call_process_execute_file_get_tid((const char*)paths.get(i), MONAPI_FALSE, &tid, msg.arg2, msg.arg2) == 0? "OK\n" : "NG\n"); } else { syscall_print(monapi_call_process_execute_file((const char*)paths.get(i), MONAPI_FALSE) == 0? "OK\n" : "NG\n"); } for (;;) { if (Message::receive(&msg)) continue; if (msg.header == MSG_STARTED) break; } } if (firstLoad) firstLoad = false; }
bool WindowHandler(MessageInfo* msg) { switch (msg->header) { // ウィンドウ生成要求 case MSG_GUISERVER_CREATEWINDOW: { guiserver_window* w = CreateWindow(); w->ThreadID = msg->from; Message::reply(msg, w->Handle); break; } // ウィンドウ破棄要求 case MSG_GUISERVER_DISPOSEWINDOW: DisposeWindow(msg->arg1); Message::reply(msg); break; // ウィンドウ描画要求 case MSG_GUISERVER_DRAWWINDOW: if (msg->arg2 != 0 && msg->arg3 != 0) { // 部分描画 DrawWindow(GetWindowPointer(msg->arg1), GET_X_DWORD(msg->arg2), GET_Y_DWORD(msg->arg2), GET_X_DWORD(msg->arg3), GET_Y_DWORD(msg->arg3), true); } else { DrawWindow(GetWindowPointer(msg->arg1), true); } Message::reply(msg); break; // ウィンドウ移動要求 case MSG_GUISERVER_MOVEWINDOW: MoveWindow(GetWindowPointer(msg->arg1), (int)msg->arg2, (int)msg->arg3); Message::reply(msg); break; // ウィンドウ最前面移動要求 case MSG_GUISERVER_WINDOWTOFRONTMOST: { guiserver_window* w = GetWindowPointer(msg->arg1); windows.remove(w); windows.add(w); if (msg->arg2 != 0) DrawWindow(w); Message::reply(msg); break; } // アクティブ化要求 case MSG_GUISERVER_ACTIVATEWINDOW: ActivateWindow(GetWindowPointer(msg->arg1)); Message::reply(msg); break; // ウィンドウ列挙要求 case MSG_GUISERVER_ENUMWINDOWS: { int size = windows.size(); int max_count = MESSAGE_INFO_MAX_STR_LENGTH / sizeof(uint32_t); // msg.str = 128 bytes int max_loop_count; if (size > max_count) { max_loop_count = max_count; printf("windows size over %d/%d %s:%d\n", max_count, size, __FILE__, __LINE__); } else { max_loop_count = size; } int i; char str[128]; for (i = 0; i < max_loop_count; i++) { guiserver_window* w = windows[i]; *((uint32_t*)(&str[i * sizeof(uint32_t)])) = w->Handle; } Message::reply(msg, max_loop_count, NULL, str); break; } // タイトル情報 case MSG_GUISERVER_GETTITLE: { guiserver_window* w = GetWindowPointer(msg->arg1); Message::reply(msg, NULL, NULL, w->name); break; } // マウス情報 case MSG_MOUSE_INFO: ProcessMouseInfo(msg); break; // キー情報 case MSG_KEY_VIRTUAL_CODE: if (msg->arg1 == MonAPI::Keys::Tab && msg->arg2 & KEY_MODIFIER_ALT) { RotateActiveWindow(); break; } ProcessKeyInfo(msg); break; // キャプチャー要求 case MSG_GUISERVER_MOUSECAPTURE: { guiserver_window* w = GetWindowPointer(msg->arg1); if (w != NULL) { if (msg->arg2 == 0) { captures.remove(w); } else { captures.add(w); } } Message::reply(msg); break; } // 移動領域作成要求 case MSG_GUISERVER_CREATEOVERLAP: { Overlap* ov = new Overlap( (int)msg->arg1, (int)msg->arg2, GET_X_DWORD(msg->arg3), GET_Y_DWORD(msg->arg3)); overlaps.add(ov); Message::reply(msg, (uint32_t)ov); break; } // 移動領域削除要求 case MSG_GUISERVER_DISPOSEOVERLAP: { Overlap* ov = (Overlap*)msg->arg1; overlaps.remove(ov); delete ov; Message::reply(msg); break; } // 移動領域移動要求 case MSG_GUISERVER_MOVEOVERLAP: ((Overlap*)msg->arg1)->Move( GET_X_DWORD(msg->arg2), GET_Y_DWORD(msg->arg2), GET_X_DWORD(msg->arg3), GET_Y_DWORD(msg->arg3)); Message::reply(msg); break; // 拡張効果要求 case MSG_GUISERVER_EXPANSIONEFFECT: ExpansionEffect( GET_X_DWORD(msg->arg1), GET_Y_DWORD(msg->arg1), GET_X_DWORD(msg->arg2), GET_Y_DWORD(msg->arg2), GET_X_DWORD(msg->arg3), GET_Y_DWORD(msg->arg3)); Message::reply(msg); break; // 縮小効果要求 case MSG_GUISERVER_REDUCTIONEFFECT: ReductionEffect( GET_X_DWORD(msg->arg1), GET_Y_DWORD(msg->arg1), GET_X_DWORD(msg->arg2), GET_Y_DWORD(msg->arg2), GET_X_DWORD(msg->arg3), GET_Y_DWORD(msg->arg3)); Message::reply(msg); break; default: return false; } return true; }
static void RotateActiveWindow() { if (windows.size() > 1) { ActivateWindow(windows[1]); } }