Source code of Windows XP (NT5)
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

670 lines
18 KiB

  1. /*++
  2. Copyright (c) 2000 Microsoft Corporation. All rights reserved.
  3. Module Name:
  4. tsrpc.cpp
  5. Abstract:
  6. This module contains the TabSrv RPC services.
  7. Author:
  8. Michael Tsang (MikeTs) 05-Jun-2000
  9. Environment:
  10. User mode
  11. Revision History:
  12. --*/
  13. #include "pch.h"
  14. /*++
  15. @doc INTERNAL
  16. @func unsigned | RPCServerThread | RPC Server thread.
  17. @parm IN PVOID | param | Not used.
  18. @rvalue Always returns 0.
  19. --*/
  20. unsigned __stdcall
  21. RPCServerThread(
  22. IN PVOID param
  23. )
  24. {
  25. TRACEPROC("RPCServerThread", 2)
  26. RPC_STATUS status;
  27. RPC_BINDING_VECTOR *BindingVector = NULL;
  28. TRACEENTER(("(param=%p)\n", param));
  29. if ((status = RpcServerUseProtseq((unsigned char *)"ncalrpc",
  30. RPC_C_PROTSEQ_MAX_REQS_DEFAULT,
  31. NULL)) != RPC_S_OK)
  32. {
  33. TABSRVERR(("RpcServerUseProtSeqEp failed (status=%d)\n", status));
  34. }
  35. else if ((status = RpcServerRegisterIf(TabSrv_v1_0_s_ifspec,
  36. NULL,
  37. NULL)) != RPC_S_OK)
  38. {
  39. TABSRVERR(("RpcServerRegisterIf failed (status=%d)\n", status));
  40. }
  41. else if ((status = RpcServerInqBindings(&BindingVector)) != RPC_S_OK)
  42. {
  43. TABSRVERR(("RpcServerInqBindings failed (status=%d)\n", status));
  44. }
  45. else if ((status = RpcEpRegister(TabSrv_v1_0_s_ifspec,
  46. BindingVector,
  47. NULL,
  48. NULL)) != RPC_S_OK)
  49. {
  50. RpcBindingVectorFree(&BindingVector);
  51. TABSRVERR(("RpcEpRegister failed (status=%d)\n", status));
  52. }
  53. else if ((status = RpcServerRegisterAuthInfo(NULL,
  54. RPC_C_AUTHN_WINNT,
  55. NULL,
  56. NULL)) != RPC_S_OK)
  57. {
  58. RpcEpUnregister(TabSrv_v1_0_s_ifspec, BindingVector, NULL);
  59. RpcBindingVectorFree(&BindingVector);
  60. TABSRVERR(("RpcServerRegisterAuthInfo failed (status=%d)\n", status));
  61. }
  62. else
  63. {
  64. status = RpcServerListen(1, RPC_C_LISTEN_MAX_CALLS_DEFAULT, FALSE);
  65. TRACEASSERT(status == RPC_S_OK);
  66. RpcEpUnregister(TabSrv_v1_0_s_ifspec, BindingVector, NULL);
  67. RpcBindingVectorFree(&BindingVector);
  68. }
  69. TRACEINFO(1, ("RPC thread exiting...\n"));
  70. TRACEEXIT(("=0\n"));
  71. return 0;
  72. } //RPCServerThread
  73. /*++
  74. @doc EXTERNAL
  75. @func HEVTNOTIFY | TabSrvRegisterEventNotify |
  76. Register event notification.
  77. @parm IN handle_t | hBinding | RPC binding handle.
  78. @parm IN EVTNOTIFY | Notify event.
  79. @parm IN HWIN | hwnd | Handle to window to be notified.
  80. @parm IN UINT | uiMsg | Notification message used.
  81. @rvalue SUCCESS | Returns notification handle.
  82. @rvalue FAILURE | Returns NULL.
  83. --*/
  84. HEVTNOTIFY
  85. TabSrvRegisterEventNotify(
  86. IN handle_t hBinding,
  87. IN EVTNOTIFY Event,
  88. IN HWIN hwnd,
  89. IN UINT uiMsg
  90. )
  91. {
  92. TRACEPROC("TabSrvRegisterEventNotify", 2)
  93. PNOTIFYCLIENT Client;
  94. TRACEENTER(("(hBinding=%x,Event=%x,hwnd=%x,Msg=%d)\n",
  95. hBinding, Event, hwnd, uiMsg));
  96. Client = (PNOTIFYCLIENT)malloc(sizeof(NOTIFYCLIENT));
  97. if (Client != NULL)
  98. {
  99. DWORD rcWait;
  100. Client->dwSig = SIG_NOTIFYCLIENT;
  101. Client->Event = Event;
  102. Client->hwnd = (HWND)hwnd;
  103. Client->uiMsg = uiMsg;
  104. rcWait = WaitForSingleObject(ghmutNotifyList, INFINITE);
  105. if (rcWait == WAIT_OBJECT_0)
  106. {
  107. InsertTailList(&glistNotifyClients, &Client->list);
  108. ReleaseMutex(ghmutNotifyList);
  109. }
  110. else
  111. {
  112. TABSRVERR(("failed to wait for client list Mutex (rcWait=%x,err=%d).\n",
  113. rcWait, GetLastError()));
  114. }
  115. }
  116. else
  117. {
  118. TABSRVERR(("Failed to allocate notification client.\n"));
  119. }
  120. TRACEEXIT(("=%p\n", Client));
  121. return (HEVTNOTIFY)Client;
  122. } //TabSrvRegisterEventNotify
  123. /*++
  124. @doc EXTERNAL
  125. @func VOID | TabSrvDeregisterEventNotify | Deregister event notification.
  126. @parm IN handle_t | hBinding | RPC binding handle.
  127. @parm IN HEVTNOTIFY | Notification handle.
  128. @rvalue SUCCESS | Returns TRUE.
  129. @rvalue FAILURE | Returns FALSE.
  130. --*/
  131. BOOL
  132. TabSrvDeregisterEventNotify(
  133. IN handle_t hBinding,
  134. IN HEVTNOTIFY hEventNotify
  135. )
  136. {
  137. TRACEPROC("TabSrvRegisterEventNotify", 2)
  138. BOOL rc;
  139. PNOTIFYCLIENT Client = (PNOTIFYCLIENT)hEventNotify;
  140. DWORD rcWait;
  141. TRACEENTER(("(hBinding=%x,NotifyClient=%p)\n", Client));
  142. __try
  143. {
  144. rc = (Client->dwSig == SIG_NOTIFYCLIENT);
  145. }
  146. __except(1)
  147. {
  148. TABSRVERR(("Invalid Notify Client handle.\n"));
  149. rc = FALSE;
  150. }
  151. if (rc == TRUE)
  152. {
  153. rcWait = WaitForSingleObject(ghmutNotifyList, INFINITE);
  154. if (rcWait == WAIT_OBJECT_0)
  155. {
  156. RemoveEntryList(&Client->list);
  157. ReleaseMutex(ghmutNotifyList);
  158. free(Client);
  159. }
  160. else
  161. {
  162. TABSRVERR(("failed to wait for notify list Mutex (rcWait=%x,err=%d).\n",
  163. rcWait, GetLastError()));
  164. rc = FALSE;
  165. }
  166. }
  167. TRACEEXIT(("=%x\n", rc));
  168. return rc;
  169. } //TabSrvDeregisterEventNotify
  170. /*++
  171. @doc EXTERNAL
  172. @func VOID | TabSrvGetLastRawDigiReport | Get the last raw digitizer
  173. report.
  174. @parm IN handle_t | hBinding | RPC binding handle.
  175. @parm OUT PWORD | pwButtonState | To hold the button state data.
  176. @parm OUT PWORD | pwX | To hold the X data.
  177. @parm OUT PWORD | pwY | To hold the Y data.
  178. @rvalue None.
  179. --*/
  180. VOID
  181. TabSrvGetLastRawDigiReport(
  182. IN handle_t hBinding,
  183. OUT PWORD pwButtonState,
  184. OUT PWORD pwX,
  185. OUT PWORD pwY
  186. )
  187. {
  188. TRACEPROC("TabSrvGetLastRawDigiReport", 2)
  189. TRACEENTER(("(hBinding=%x,pwButtonState=%p,pwX=%p,pwY=%p)\n",
  190. hBinding, pwButtonState, pwX, pwY));
  191. *pwButtonState = gLastRawDigiReport.wButtonState;
  192. *pwX = gLastRawDigiReport.wX;
  193. *pwY = gLastRawDigiReport.wY;
  194. TRACEEXIT(("!\n"));
  195. return;
  196. } //TabSrvGetLastRawDigiReport
  197. /*++
  198. @doc EXTERNAL
  199. @func VOID | TabSrvSetPenTilt | Set pen tilt compensation.
  200. @parm IN handle_t | hBinding | RPC binding handle.
  201. @parm IN LONG | dx | x compensation.
  202. @parm IN LONG | dy | y compensation.
  203. @rvalue None.
  204. --*/
  205. VOID
  206. TabSrvSetPenTilt(
  207. IN handle_t hBinding,
  208. IN LONG dx,
  209. IN LONG dy
  210. )
  211. {
  212. TRACEPROC("TabSrvSetPenTilt", 2)
  213. LPTSTR lptstrPenTilt;
  214. TRACEENTER(("(hBinding=%x,dx=%d,dy=%d)\n", hBinding, dx, dy));
  215. lptstrPenTilt = (gdwfTabSrv & TSF_PORTRAIT_MODE)? TEXT("PenTilt_Portrait"):
  216. TEXT("PenTilt_Landscape");
  217. gConfig.PenTilt.dx = dx;
  218. gConfig.PenTilt.dy = dy;
  219. WriteConfig(lptstrPenTilt,
  220. REG_BINARY,
  221. (LPBYTE)&gConfig.PenTilt,
  222. sizeof(gConfig.PenTilt));
  223. TRACEEXIT(("!\n"));
  224. return;
  225. } //TabSrvSetPenTilt
  226. /*++
  227. @doc EXTERNAL
  228. @func BOOL | TabSrvGetLinearityMap | Get linearity map.
  229. @parm IN handle_t | hBinding | RPC binding handle.
  230. @parm OUT PLINEARITY_MAP | LinearityMap | Points to the linearity map.
  231. @rvalue SUCCESS | Returns TRUE.
  232. @rvalue FAILURE | Returns FALSE.
  233. --*/
  234. BOOL
  235. TabSrvGetLinearityMap(
  236. IN handle_t hBinding,
  237. OUT PLINEAR_MAP LinearityMap
  238. )
  239. {
  240. TRACEPROC("TabSrvGetLinearityMap", 2)
  241. BOOL rc;
  242. TRACEENTER(("(hBinding=%x,pLinearityMap=%p)\n", hBinding, LinearityMap));
  243. if (gdwfTabSrv & TSF_HAS_LINEAR_MAP)
  244. {
  245. *LinearityMap = gConfig.LinearityMap;
  246. rc = TRUE;
  247. }
  248. else
  249. {
  250. rc = FALSE;
  251. }
  252. TRACEEXIT(("=%x\n", rc));
  253. return rc;
  254. } //TabSrvGetLinearityMap
  255. /*++
  256. @doc EXTERNAL
  257. @func VOID | TabSrvSetLinearityMap | Set linearity map.
  258. @parm IN handle_t | hBinding | RPC binding handle.
  259. @parm IN PLINEARITY_MAP | LinearityMap | Points to the linearity map.
  260. @rvalue None.
  261. --*/
  262. VOID
  263. TabSrvSetLinearityMap(
  264. IN handle_t hBinding,
  265. IN PLINEAR_MAP LinearityMap
  266. )
  267. {
  268. TRACEPROC("TabSrvSetLinearityMap", 2)
  269. TRACEENTER(("(hBinding=%x,pLinearityMap=%p)\n", hBinding, LinearityMap));
  270. gConfig.LinearityMap = *LinearityMap;
  271. WriteConfig(gtszLinearityMap,
  272. REG_BINARY,
  273. (LPBYTE)&gConfig.LinearityMap,
  274. sizeof(gConfig.LinearityMap));
  275. gdwfTabSrv |= TSF_HAS_LINEAR_MAP;
  276. TRACEEXIT(("!\n"));
  277. return;
  278. } //TabSrvSetLinearityMap
  279. /*++
  280. @doc EXTERNAL
  281. @func BOOL | TabSrvGetPenFeatures | Get digitizer feature report.
  282. @parm IN handle_t | hBinding | RPC binding handle.
  283. @parm IN WORD | wReportID | Report ID of the feature report.
  284. @parm IN WORD | wUsagePage | Usage page of the digitizer.
  285. @parm IN WORD | wUsage | Usage of the digitizer page.
  286. @parm OUT DWORD * | pdwFeature | To hold the feature value.
  287. @rvalue SUCCESS | Returns TRUE.
  288. @rvalue FAILURE | Returns FALSE.
  289. --*/
  290. BOOL
  291. TabSrvGetPenFeatures(
  292. IN handle_t hBinding,
  293. IN WORD wReportID,
  294. IN WORD wUsagePage,
  295. IN WORD wUsage,
  296. OUT DWORD *pdwFeature
  297. )
  298. {
  299. TRACEPROC("TabSrvGetPenFeatures", 2)
  300. BOOL rc = FALSE;
  301. PCHAR buff;
  302. TRACEENTER(("(hBinding=%x,ReportID=%d,UsagePage=%d,Usage=%d,pdwFeature=%p)\n",
  303. hBinding, wReportID, wUsagePage, wUsage, pdwFeature));
  304. if (gdevDigitizer.hDevice != INVALID_HANDLE_VALUE)
  305. {
  306. buff = (PCHAR)calloc(gdevDigitizer.hidCaps.FeatureReportByteLength,
  307. sizeof(CHAR));
  308. TRACEASSERT(buff != NULL);
  309. *buff = (CHAR)wReportID;
  310. rc = HidD_GetFeature(gdevDigitizer.hDevice,
  311. buff,
  312. gdevDigitizer.hidCaps.FeatureReportByteLength);
  313. if (rc == TRUE)
  314. {
  315. NTSTATUS status;
  316. status = HidP_GetUsageValue(
  317. HidP_Feature,
  318. wUsagePage,
  319. 0,
  320. wUsage,
  321. pdwFeature,
  322. gdevDigitizer.pPreParsedData,
  323. buff,
  324. gdevDigitizer.hidCaps.FeatureReportByteLength);
  325. if (status != HIDP_STATUS_SUCCESS)
  326. {
  327. rc = FALSE;
  328. TABSRVERR(("Failed to get feature value (status=%x).\n",
  329. status));
  330. }
  331. }
  332. else
  333. {
  334. TABSRVERR(("Failed to get device feature.\n"));
  335. }
  336. if (buff != NULL)
  337. {
  338. free(buff);
  339. }
  340. }
  341. TRACEEXIT(("=%x (Feature=%x)\n", *pdwFeature));
  342. return rc;
  343. } //TabSrvGetPenFeatures
  344. /*++
  345. @doc EXTERNAL
  346. @func BOOL | TabSrvSetPenFeatures | Set digitizer feature report.
  347. @parm IN handle_t | hBinding | RPC binding handle.
  348. @parm IN WORD | wReportID | Report ID of the feature report.
  349. @parm IN WORD | wUsagePage | Usage page of the digitizer.
  350. @parm IN WORD | wUsage | Usage of the digitizer page.
  351. @parm IN DWORD | dwFeature | Feature value.
  352. @rvalue SUCCESS | Returns TRUE.
  353. @rvalue FAILURE | Returns FALSE.
  354. --*/
  355. BOOL
  356. TabSrvSetPenFeatures(
  357. IN handle_t hBinding,
  358. IN WORD wReportID,
  359. IN WORD wUsagePage,
  360. IN WORD wUsage,
  361. IN DWORD dwFeature
  362. )
  363. {
  364. TRACEPROC("TabSrvSetPenFeatures", 2)
  365. BOOL rc = FALSE;
  366. PCHAR buff;
  367. NTSTATUS status;
  368. TRACEENTER(("(hBinding=%x,ReportID=%d,UsagePage=%d,Usage=%d,Feature=%x)\n",
  369. hBinding, wReportID, wUsagePage, wUsage, dwFeature));
  370. if (gdevDigitizer.hDevice != INVALID_HANDLE_VALUE)
  371. {
  372. buff = (PCHAR)calloc(gdevDigitizer.hidCaps.FeatureReportByteLength,
  373. sizeof(CHAR));
  374. TRACEASSERT(buff != NULL);
  375. *buff = (CHAR)wReportID;
  376. status = HidP_SetUsageValue(
  377. HidP_Feature,
  378. wUsagePage,
  379. 0,
  380. wUsage,
  381. dwFeature,
  382. gdevDigitizer.pPreParsedData,
  383. buff,
  384. gdevDigitizer.hidCaps.FeatureReportByteLength);
  385. if (status == HIDP_STATUS_SUCCESS)
  386. {
  387. rc = HidD_SetFeature(gdevDigitizer.hDevice,
  388. buff,
  389. gdevDigitizer.hidCaps.FeatureReportByteLength);
  390. if (rc == FALSE)
  391. {
  392. TABSRVERR(("Failed to set device feature.\n"));
  393. }
  394. }
  395. else
  396. {
  397. TABSRVERR(("Failed to set feature value (status=%x).\n", status));
  398. }
  399. if (buff != NULL)
  400. {
  401. free(buff);
  402. }
  403. }
  404. TRACEEXIT(("=%x\n", rc));
  405. return rc;
  406. } //TabSrvSetPenFeatures
  407. /*++
  408. @doc EXTERNAL
  409. @func BOOL | TabSrvGetGestureSettings | Get gesture settings.
  410. @parm IN handle_t | hBinding | RPC binding handle.
  411. @parm OUT PGESTURE_SETTINGS | GestureSettings | To hold the gesture
  412. settings.
  413. @rvalue SUCCESS | Returns TRUE.
  414. @rvalue FAILURE | Returns FALSE.
  415. --*/
  416. BOOL
  417. TabSrvGetGestureSettings(
  418. IN handle_t hBinding,
  419. OUT PGESTURE_SETTINGS GestureSettings
  420. )
  421. {
  422. TRACEPROC("TabSrvGetGestureSettings", 2)
  423. TRACEENTER(("(hBinding=%x,pSettings=%p)\n", hBinding, GestureSettings));
  424. *GestureSettings = gConfig.GestureSettings;
  425. TRACEEXIT(("=1 (Features=%x,Radius=%d,StopDist=%d,StopTime=%d)\n",
  426. GestureSettings->dwfFeatures, GestureSettings->iRadius,
  427. GestureSettings->iStopDist, GestureSettings->iStopTime));
  428. return TRUE;
  429. } //TabSrvGetGestureSettings
  430. /*++
  431. @doc EXTERNAL
  432. @func BOOL | TabSrvSetGestureSettings | Set gesture settings.
  433. @parm IN handle_t | hBinding | RPC binding handle.
  434. @parm IN PGESTURE_SETTINGS | GestureSettings | Point to the gesture
  435. settings to set.
  436. @rvalue SUCCESS | Returns TRUE.
  437. @rvalue FAILURE | Returns FALSE.
  438. --*/
  439. BOOL
  440. TabSrvSetGestureSettings(
  441. IN handle_t hBinding,
  442. IN PGESTURE_SETTINGS GestureSettings
  443. )
  444. {
  445. TRACEPROC("TabSrvSetGestureSettings", 2)
  446. BOOL rc = FALSE;
  447. PTSTHREAD MouseThread;
  448. TRACEENTER(("(hBinding=%x,pSettings=%p,Features=%x,Radius=%d,StopDist=%d,StopTime=%d)\n",
  449. hBinding, GestureSettings, GestureSettings->dwfFeatures,
  450. GestureSettings->iRadius, GestureSettings->iStopDist,
  451. GestureSettings->iStopTime));
  452. gConfig.GestureSettings = *GestureSettings;
  453. WriteConfig(gtszGestureSettings,
  454. REG_BINARY,
  455. (LPBYTE)&gConfig.GestureSettings,
  456. sizeof(gConfig.GestureSettings));
  457. MouseThread = FindThread(TSF_MOUSETHREAD);
  458. if (MouseThread != NULL)
  459. {
  460. if (gConfig.GestureSettings.dwfFeatures & GESTURE_FEATURE_MOUSE_ENABLED)
  461. {
  462. MouseThread->dwfThread |= THREADF_ENABLED;
  463. }
  464. else
  465. {
  466. MouseThread->dwfThread &= ~THREADF_ENABLED;
  467. }
  468. if ((MouseThread->dwfThread & THREADF_ENABLED) &&
  469. (MouseThread->hThread == NULL))
  470. {
  471. //
  472. // Mouse thread is enabled but not running, so start it.
  473. //
  474. if (!InitThreads(MouseThread, 1))
  475. {
  476. TABSRVERR(("failed to start mouse thread.\n"));
  477. }
  478. }
  479. else if (!(MouseThread->dwfThread & THREADF_ENABLED) &&
  480. (MouseThread->hThread != NULL))
  481. {
  482. //
  483. // Mouse thread is disabled but it is currently running, so kill it.
  484. //
  485. if (ghwndMouse != NULL)
  486. {
  487. DWORD rcWait;
  488. gdwfTabSrv |= TSF_TERMINATE;
  489. PostMessage(ghwndMouse, WM_CLOSE, 0, 0);
  490. rcWait = WaitForSingleObject(MouseThread->hThread, 1000);
  491. if (rcWait != WAIT_OBJECT_0)
  492. {
  493. TABSRVERR(("failed to kill mouse thread (rcWait=%x,err=%d)\n",
  494. rcWait, GetLastError()));
  495. }
  496. gdwfTabSrv &= ~TSF_TERMINATE;
  497. }
  498. }
  499. }
  500. TRACEEXIT(("=1\n"));
  501. return TRUE;
  502. } //TabSrvSetGestureSettings
  503. /*++
  504. @doc EXTERNAL
  505. @func BOOL | TabSrvGetButtonSettings | Get button settings.
  506. @parm IN handle_t | hBinding | RPC binding handle.
  507. @parm OUT PBUTTON_SETTINGS | ButtonSettings | To hold the button
  508. settings.
  509. @rvalue SUCCESS | Returns TRUE.
  510. @rvalue FAILURE | Returns FALSE.
  511. --*/
  512. BOOL
  513. TabSrvGetButtonSettings(
  514. IN handle_t hBinding,
  515. OUT PBUTTON_SETTINGS ButtonSettings
  516. )
  517. {
  518. TRACEPROC("TabSrvGetButtonSettings", 2)
  519. TRACEENTER(("(hBinding=%x,pSettings=%p)\n", hBinding, ButtonSettings));
  520. *ButtonSettings = gConfig.ButtonSettings;
  521. TRACEEXIT(("=1\n"));
  522. return TRUE;
  523. } //TabSrvGetButtonSettings
  524. /*++
  525. @doc EXTERNAL
  526. @func BOOL | TabSrvSetButtonSettings | Set button settings.
  527. @parm IN handle_t | hBinding | RPC binding handle.
  528. @parm IN PBUTTON_SETTINGS | ButtonSettings | Point to the button
  529. settings to set.
  530. @rvalue SUCCESS | Returns TRUE.
  531. @rvalue FAILURE | Returns FALSE.
  532. --*/
  533. BOOL
  534. TabSrvSetButtonSettings(
  535. IN handle_t hBinding,
  536. IN PBUTTON_SETTINGS ButtonSettings
  537. )
  538. {
  539. TRACEPROC("TabSrvSetButtonSettings", 2)
  540. BOOL rc = FALSE;
  541. PTSTHREAD MouseThread;
  542. TRACEENTER(("(hBinding=%x,pSettings=%p)\n", hBinding, ButtonSettings));
  543. gConfig.ButtonSettings = *ButtonSettings;
  544. WriteConfig(gtszButtonSettings,
  545. REG_BINARY,
  546. (LPBYTE)&gConfig.ButtonSettings,
  547. sizeof(gConfig.ButtonSettings));
  548. TRACEEXIT(("=1\n"));
  549. return TRUE;
  550. } //TabSrvSetGestureSettings