/filesystems/procfs/procfs.cc

http://macfuse.googlecode.com/ · C++ · 4975 lines · 4101 code · 796 blank · 78 comment · 606 complexity · 8905523075cf982ed57d446bcdf473d7 MD5 · raw file

Large files are truncated click here to view the full file

  1. /*
  2. * procfs as a MacFUSE file system for Mac OS X
  3. *
  4. * Copyright Amit Singh. All Rights Reserved.
  5. * http://osxbook.com
  6. *
  7. * http://code.google.com/p/macfuse/
  8. *
  9. * Source License: GNU GENERAL PUBLIC LICENSE (GPL)
  10. */
  11. #define MACFUSE_PROCFS_VERSION "2.0"
  12. #define FUSE_USE_VERSION 26
  13. #include <dirent.h>
  14. #include <errno.h>
  15. #include <fcntl.h>
  16. #include <getopt.h>
  17. #include <pthread.h>
  18. #include <stdio.h>
  19. #include <string.h>
  20. #include <sys/sysctl.h>
  21. #include <grp.h>
  22. #include <pwd.h>
  23. #include <mach/mach.h>
  24. #include <mach/mach_vm.h>
  25. #include <mach/vm_region.h>
  26. #include <mach/vm_statistics.h>
  27. #include <Carbon/Carbon.h>
  28. #include <CoreFoundation/CoreFoundation.h>
  29. #include <IOKit/IOKitLib.h>
  30. #include <cassert>
  31. #include <vector>
  32. #include <pcrecpp.h>
  33. #include <fuse.h>
  34. #include "procfs_displays.h"
  35. #include "procfs_proc_info.h"
  36. #include "procfs_windows.h"
  37. #include "sequencegrab/procfs_sequencegrab.h"
  38. #if MACFUSE_PROCFS_ENABLE_TPM
  39. #include "procfs_tpm.h"
  40. #endif /* MACFUSE_PROCFS_ENABLE_TPM */
  41. static int procfs_ui = 0;
  42. #define PROCFS_DEFAULT_FILE_SIZE 65536
  43. static int total_file_patterns = 0;
  44. static int total_directory_patterns = 0;
  45. static int total_link_patterns = 0;
  46. static processor_port_array_t processor_list;
  47. static mach_port_t p_default_set = 0;
  48. static mach_port_t p_default_set_control = 0;
  49. static host_priv_t host_priv;
  50. static natural_t processor_count = 0;
  51. static io_connect_t lightsensor_port = 0;
  52. static io_connect_t motionsensor_port = 0;
  53. static unsigned int sms_gIndex = 0;
  54. static IOItemCount sms_gStructureInputSize = 0;
  55. static IOByteCount sms_gStructureOutputSize = 0;
  56. /* camera */
  57. static pthread_mutex_t camera_lock;
  58. static int camera_busy = 0;
  59. static CFMutableDataRef camera_tiff = (CFMutableDataRef)0;
  60. /* display */
  61. static pthread_mutex_t display_lock;
  62. static int display_busy = 0;
  63. static CFMutableDataRef display_png = (CFMutableDataRef)0;
  64. static pcrecpp::RE *valid_process_pattern = new pcrecpp::RE("/(\\d+)");
  65. typedef struct {
  66. char x;
  67. char y;
  68. char z;
  69. short v;
  70. #define FILLER_SIZE 60
  71. char scratch[FILLER_SIZE];
  72. } MotionSensorData_t;
  73. static kern_return_t
  74. sms_getOrientation_hardware_apple(MotionSensorData_t *odata)
  75. {
  76. kern_return_t kr;
  77. IOItemCount isize = sms_gStructureInputSize;
  78. IOByteCount osize = sms_gStructureOutputSize;
  79. MotionSensorData_t idata;
  80. kr = IOConnectMethodStructureIStructureO(motionsensor_port,
  81. sms_gIndex,
  82. isize,
  83. &osize,
  84. &idata,
  85. odata);
  86. return kr;
  87. }
  88. static int init_task_list(task_array_t *task_list,
  89. mach_msg_type_number_t *task_count)
  90. {
  91. return processor_set_tasks(p_default_set_control, task_list, task_count);
  92. }
  93. static void fini_task_list(task_array_t task_list,
  94. mach_msg_type_number_t task_count)
  95. {
  96. unsigned int i;
  97. for (i = 0; i < task_count; i++) {
  98. mach_port_deallocate(mach_task_self(), task_list[i]);
  99. }
  100. vm_deallocate(mach_task_self(), (vm_address_t)task_list,
  101. task_count * sizeof(task_t));
  102. }
  103. static int init_thread_list(task_t the_task,
  104. thread_array_t *thread_list,
  105. mach_msg_type_number_t *thread_count)
  106. {
  107. return task_threads(the_task, thread_list, thread_count);
  108. }
  109. static void fini_thread_list(thread_array_t thread_list,
  110. mach_msg_type_number_t thread_count)
  111. {
  112. unsigned int i;
  113. for (i = 0; i < thread_count; i++) {
  114. mach_port_deallocate(mach_task_self(), thread_list[i]);
  115. }
  116. vm_deallocate(mach_task_self(), (vm_address_t)thread_list,
  117. thread_count * sizeof(thread_act_t));
  118. }
  119. static int init_port_list(task_t the_task,
  120. mach_port_name_array_t *name_list,
  121. mach_msg_type_number_t *name_count,
  122. mach_port_type_array_t *type_list,
  123. mach_msg_type_number_t *type_count)
  124. {
  125. return mach_port_names(the_task,
  126. name_list, name_count, type_list, type_count);
  127. }
  128. static void fini_port_list(mach_port_name_array_t name_list,
  129. mach_msg_type_number_t name_count,
  130. mach_port_type_array_t type_list,
  131. mach_msg_type_number_t type_count)
  132. {
  133. vm_deallocate(mach_task_self(), (vm_address_t)name_list,
  134. name_count * sizeof(mach_port_name_t));
  135. vm_deallocate(mach_task_self(), (vm_address_t)type_list,
  136. type_count * sizeof(mach_port_type_t));
  137. }
  138. #define DECL_PORT_LIST() \
  139. mach_port_name_array_t name_list; \
  140. mach_msg_type_number_t name_count; \
  141. mach_port_type_array_t type_list; \
  142. mach_msg_type_number_t type_count;
  143. #define INIT_PORT_LIST(the_task) \
  144. if (init_port_list(the_task, &name_list, &name_count, &type_list, &type_count) != 0) { \
  145. return -EIO; \
  146. }
  147. #define FINI_PORT_LIST() \
  148. fini_port_list(name_list, name_count, type_list, type_count)
  149. #define DECL_TASK_LIST() \
  150. task_array_t task_list; \
  151. mach_msg_type_number_t task_count;
  152. #define INIT_TASK_LIST() \
  153. if (init_task_list(&task_list, &task_count) != 0) { return -EIO; }
  154. #define FINI_TASK_LIST() \
  155. fini_task_list(task_list, task_count)
  156. #define DECL_THREAD_LIST() \
  157. thread_array_t thread_list; \
  158. mach_msg_type_number_t thread_count;
  159. #define INIT_THREAD_LIST(the_task) \
  160. if (init_thread_list(the_task, &thread_list, &thread_count) != 0) { \
  161. return -EIO; \
  162. }
  163. #define FINI_THREAD_LIST() \
  164. fini_thread_list(thread_list, thread_count)
  165. struct procfs_dispatcher_entry;
  166. typedef struct procfs_dispatcher_entry * procfs_dispatcher_entry_t;
  167. typedef int (*procfs_open_handler_t)(procfs_dispatcher_entry_t e,
  168. const char *argv[],
  169. const char *path,
  170. struct fuse_file_info *fi);
  171. typedef int (*procfs_release_handler_t)(procfs_dispatcher_entry_t e,
  172. const char *argv[],
  173. const char *path,
  174. struct fuse_file_info *fi);
  175. typedef int (*procfs_opendir_handler_t)(procfs_dispatcher_entry_t e,
  176. const char *argv[],
  177. const char *path,
  178. struct fuse_file_info *fi);
  179. typedef int (*procfs_releasedir_handler_t)(procfs_dispatcher_entry_t e,
  180. const char *argv[],
  181. const char *path,
  182. struct fuse_file_info *fi);
  183. typedef int (*procfs_getattr_handler_t)(procfs_dispatcher_entry_t e,
  184. const char *argv[],
  185. struct stat *stbuf);
  186. typedef int (*procfs_read_handler_t)(procfs_dispatcher_entry_t e,
  187. const char *argv[],
  188. char *buf,
  189. size_t size,
  190. off_t offset,
  191. struct fuse_file_info *fi);
  192. typedef int (*procfs_readdir_handler_t)(procfs_dispatcher_entry_t e,
  193. const char *argv[],
  194. void *buf,
  195. fuse_fill_dir_t filler,
  196. off_t offset,
  197. struct fuse_file_info *fi);
  198. typedef int (*procfs_readlink_handler_t)(procfs_dispatcher_entry_t e,
  199. const char *argv[],
  200. char *buf,
  201. size_t size);
  202. typedef struct procfs_dispatcher_entry {
  203. int flag;
  204. char *pattern;
  205. pcrecpp::RE *compiled_pattern;
  206. int argc;
  207. procfs_open_handler_t open;
  208. procfs_release_handler_t release;
  209. procfs_opendir_handler_t opendir;
  210. procfs_releasedir_handler_t releasedir;
  211. procfs_getattr_handler_t getattr;
  212. procfs_read_handler_t read;
  213. procfs_readdir_handler_t readdir;
  214. procfs_readlink_handler_t readlink;
  215. const char *content_files[32];
  216. const char *content_directories[32];
  217. };
  218. /* flags */
  219. #define PROCFS_FLAG_ISDOTFILE 0x00000001
  220. #define PROCFS_MAX_ARGS 3
  221. #define OPEN_HANDLER(handler) \
  222. int \
  223. procfs_open_##handler(procfs_dispatcher_entry_t e, \
  224. const char *argv[], \
  225. const char *path, \
  226. struct fuse_file_info *fi) \
  227. #define RELEASE_HANDLER(handler) \
  228. int \
  229. procfs_release_##handler(procfs_dispatcher_entry_t e, \
  230. const char *argv[], \
  231. const char *path, \
  232. struct fuse_file_info *fi) \
  233. #define OPENDIR_HANDLER(handler) \
  234. int \
  235. procfs_opendir_##handler(procfs_dispatcher_entry_t e, \
  236. const char *argv[], \
  237. const char *path, \
  238. struct fuse_file_info *fi) \
  239. #define RELEASEDIR_HANDLER(handler) \
  240. int \
  241. procfs_releasedir_##handler(procfs_dispatcher_entry_t e, \
  242. const char *argv[], \
  243. const char *path, \
  244. struct fuse_file_info *fi) \
  245. #define GETATTR_HANDLER(handler) \
  246. int \
  247. procfs_getattr_##handler(procfs_dispatcher_entry_t e, \
  248. const char *argv[], \
  249. struct stat *stbuf) \
  250. #define READ_HANDLER(handler) \
  251. int \
  252. procfs_read_##handler(procfs_dispatcher_entry_t e, \
  253. const char *argv[], \
  254. char *buf, \
  255. size_t size, \
  256. off_t offset, \
  257. struct fuse_file_info *fi) \
  258. #define READDIR_HANDLER(handler) \
  259. int \
  260. procfs_readdir_##handler(procfs_dispatcher_entry_t e, \
  261. const char *argv[], \
  262. void *buf, \
  263. fuse_fill_dir_t filler, \
  264. off_t offset, \
  265. struct fuse_file_info *fi) \
  266. #define READLINK_HANDLER(handler) \
  267. int \
  268. procfs_readlink_##handler(procfs_dispatcher_entry_t e, \
  269. const char *argv[], \
  270. char *buf, \
  271. size_t size) \
  272. #define PROTO_OPEN_HANDLER(handler) OPEN_HANDLER(handler)
  273. #define PROTO_RELEASE_HANDLER(handler) RELEASE_HANDLER(handler)
  274. #define PROTO_OPENDIR_HANDLER(handler) OPENDIR_HANDLER(handler)
  275. #define PROTO_RELEASEDIR_HANDLER(handler) RELEASEDIR_HANDLER(handler)
  276. #define PROTO_READ_HANDLER(handler) READ_HANDLER(handler)
  277. #define PROTO_READDIR_HANDLER(handler) READDIR_HANDLER(handler)
  278. #define PROTO_READLINK_HANDLER(handler) READLINK_HANDLER(handler)
  279. #define PROTO_GETATTR_HANDLER(handler) GETATTR_HANDLER(handler)
  280. #define DECL_FILE(pattern, argc, openp, releasep, getattrp, readp) \
  281. { \
  282. 0, \
  283. pattern, \
  284. new pcrecpp::RE(pattern), \
  285. argc, \
  286. procfs_open_##openp, \
  287. procfs_release_##releasep, \
  288. procfs_opendir_enotdir, \
  289. procfs_releasedir_enotdir, \
  290. procfs_getattr_##getattrp, \
  291. procfs_read_##readp, \
  292. procfs_readdir_enotdir, \
  293. procfs_readlink_einval, \
  294. { NULL }, \
  295. { NULL } \
  296. },
  297. #define DECL_FILE_WITHFLAGS(flag, pattern, argc, openp, releasep, getattrp, readp) \
  298. { \
  299. flag, \
  300. pattern, \
  301. new pcrecpp::RE(pattern), \
  302. argc, \
  303. procfs_open_##openp, \
  304. procfs_release_##releasep, \
  305. procfs_opendir_enotdir, \
  306. procfs_releasedir_enotdir, \
  307. procfs_getattr_##getattrp, \
  308. procfs_read_##readp, \
  309. procfs_readdir_enotdir, \
  310. procfs_readlink_einval, \
  311. { NULL }, \
  312. { NULL } \
  313. },
  314. #define DECL_DIRECTORY(pattern, argc, opendirp, releasedirp, getattrp, readdirp, contents, ...) \
  315. { \
  316. 0, \
  317. pattern, \
  318. new pcrecpp::RE(pattern), \
  319. argc, \
  320. procfs_open_eisdir, \
  321. procfs_release_eisdir, \
  322. procfs_opendir_##opendirp, \
  323. procfs_releasedir_##releasedirp, \
  324. procfs_getattr_##getattrp, \
  325. procfs_read_eisdir, \
  326. procfs_readdir_##readdirp, \
  327. procfs_readlink_einval, \
  328. contents, \
  329. __VA_ARGS__ \
  330. },
  331. #define DECL_DIRECTORY_COMPACT(pattern, contents, ...) \
  332. { \
  333. 0, \
  334. pattern, \
  335. new pcrecpp::RE(pattern), \
  336. 0, \
  337. procfs_open_eisdir, \
  338. procfs_release_eisdir, \
  339. procfs_opendir_default_directory, \
  340. procfs_releasedir_default_directory, \
  341. procfs_getattr_default_directory, \
  342. procfs_read_eisdir, \
  343. procfs_readdir_default, \
  344. procfs_readlink_einval, \
  345. contents, \
  346. ##__VA_ARGS__ \
  347. },
  348. #define DECL_LINK(pattern, argc, openp, releasep, getattrp, readlinkp) \
  349. { \
  350. 0, \
  351. pattern, \
  352. new pcrecpp::RE(pattern), \
  353. argc, \
  354. procfs_open_##openp, \
  355. procfs_release_##releasep, \
  356. procfs_opendir_enotdir, \
  357. procfs_releasedir_enotdir, \
  358. procfs_getattr_##getattrp, \
  359. procfs_read_einval, \
  360. procfs_readdir_enotdir, \
  361. procfs_readlink_##readlinkp, \
  362. { NULL }, \
  363. { NULL } \
  364. },
  365. #define DECL_LINK_COMPACT(pattern, argc, readlinkp) \
  366. { \
  367. 0, \
  368. pattern, \
  369. new pcrecpp::RE(pattern), \
  370. argc, \
  371. procfs_open_default_file, \
  372. procfs_release_default_file, \
  373. procfs_opendir_enotdir, \
  374. procfs_releasedir_enotdir, \
  375. procfs_getattr_default_link, \
  376. procfs_read_einval, \
  377. procfs_readdir_enotdir, \
  378. procfs_readlink_##readlinkp, \
  379. { NULL }, \
  380. { NULL } \
  381. },
  382. PROTO_OPEN_HANDLER(default_file);
  383. PROTO_OPEN_HANDLER(eisdir);
  384. PROTO_OPEN_HANDLER(proc__windows__identify);
  385. PROTO_OPEN_HANDLER(proc__windows__screenshots__window);
  386. PROTO_OPEN_HANDLER(system__hardware__camera__screenshot);
  387. PROTO_OPEN_HANDLER(system__hardware__displays__display__screenshot);
  388. PROTO_RELEASE_HANDLER(default_file);
  389. PROTO_RELEASE_HANDLER(eisdir);
  390. PROTO_RELEASE_HANDLER(proc__windows__identify);
  391. PROTO_RELEASE_HANDLER(proc__windows__screenshots__window);
  392. PROTO_RELEASE_HANDLER(system__hardware__camera__screenshot);
  393. PROTO_RELEASE_HANDLER(system__hardware__displays__display__screenshot);
  394. PROTO_OPENDIR_HANDLER(default_directory);
  395. PROTO_OPENDIR_HANDLER(enotdir);
  396. PROTO_RELEASEDIR_HANDLER(default_directory);
  397. PROTO_RELEASEDIR_HANDLER(enotdir);
  398. PROTO_GETATTR_HANDLER(default_file);
  399. PROTO_GETATTR_HANDLER(default_file_finder_info);
  400. PROTO_GETATTR_HANDLER(default_directory);
  401. PROTO_GETATTR_HANDLER(default_link);
  402. PROTO_GETATTR_HANDLER(byname__name);
  403. PROTO_GETATTR_HANDLER(system__hardware__camera__screenshot);
  404. PROTO_GETATTR_HANDLER(system__hardware__displays__display);
  405. PROTO_GETATTR_HANDLER(system__hardware__displays__display__screenshot);
  406. #if MACFUSE_PROCFS_ENABLE_TPM
  407. PROTO_GETATTR_HANDLER(system__hardware__tpm__keyslots__slot);
  408. PROTO_GETATTR_HANDLER(system__hardware__tpm__pcrs__pcr);
  409. #endif /* MACFUSE_PROCFS_ENABLE_TPM */
  410. PROTO_GETATTR_HANDLER(proc__task__ports__port);
  411. PROTO_GETATTR_HANDLER(proc__task__threads__thread);
  412. PROTO_GETATTR_HANDLER(proc__windows__screenshots__window);
  413. PROTO_READ_HANDLER(einval);
  414. PROTO_READ_HANDLER(eisdir);
  415. PROTO_READ_HANDLER(zero);
  416. PROTO_READ_HANDLER(default_file_finder_info);
  417. PROTO_READ_HANDLER(proc__carbon);
  418. #if __i386__
  419. PROTO_READ_HANDLER(proc__fds);
  420. #endif /* __i386__ */
  421. PROTO_READ_HANDLER(proc__generic);
  422. PROTO_READ_HANDLER(proc__task__absolutetime_info);
  423. PROTO_READ_HANDLER(proc__task__basic_info);
  424. PROTO_READ_HANDLER(proc__task__events_info);
  425. PROTO_READ_HANDLER(proc__task__thread_times_info);
  426. PROTO_READ_HANDLER(proc__task__mach_name);
  427. PROTO_READ_HANDLER(proc__task__ports__port);
  428. PROTO_READ_HANDLER(proc__task__role);
  429. PROTO_READ_HANDLER(proc__task__threads__thread__basic_info);
  430. PROTO_READ_HANDLER(proc__task__threads__thread__states__debug);
  431. PROTO_READ_HANDLER(proc__task__threads__thread__states__exception);
  432. PROTO_READ_HANDLER(proc__task__threads__thread__states__float);
  433. PROTO_READ_HANDLER(proc__task__threads__thread__states__thread);
  434. PROTO_READ_HANDLER(proc__task__tokens);
  435. PROTO_READ_HANDLER(proc__task__vmmap);
  436. PROTO_READ_HANDLER(proc__task__vmmap_r);
  437. PROTO_READ_HANDLER(proc__windows__generic);
  438. PROTO_READ_HANDLER(proc__windows__screenshots__window);
  439. PROTO_READ_HANDLER(proc__xcred);
  440. PROTO_READ_HANDLER(system__firmware__variables);
  441. PROTO_READ_HANDLER(system__hardware__camera__screenshot);
  442. PROTO_READ_HANDLER(system__hardware__cpus__cpu__data);
  443. PROTO_READ_HANDLER(system__hardware__displays__display__info);
  444. PROTO_READ_HANDLER(system__hardware__displays__display__screenshot);
  445. #if MACFUSE_PROCFS_ENABLE_TPM
  446. PROTO_READ_HANDLER(system__hardware__tpm__hwmodel);
  447. PROTO_READ_HANDLER(system__hardware__tpm__hwvendor);
  448. PROTO_READ_HANDLER(system__hardware__tpm__hwversion);
  449. PROTO_READ_HANDLER(system__hardware__tpm__keyslots__slot);
  450. PROTO_READ_HANDLER(system__hardware__tpm__pcrs__pcr);
  451. #endif /* MACFUSE_PROCFS_ENABLE_TPM */
  452. PROTO_READ_HANDLER(system__hardware__xsensor);
  453. PROTO_READDIR_HANDLER(default);
  454. PROTO_READDIR_HANDLER(enotdir);
  455. PROTO_READDIR_HANDLER(byname);
  456. PROTO_READDIR_HANDLER(proc__task__ports);
  457. PROTO_READDIR_HANDLER(proc__task__threads);
  458. PROTO_READDIR_HANDLER(proc__windows__screenshots);
  459. PROTO_READDIR_HANDLER(root);
  460. PROTO_READDIR_HANDLER(system__hardware__cpus);
  461. PROTO_READDIR_HANDLER(system__hardware__cpus__cpu);
  462. PROTO_READDIR_HANDLER(system__hardware__displays);
  463. PROTO_READDIR_HANDLER(system__hardware__displays__display);
  464. #if MACFUSE_PROCFS_ENABLE_TPM
  465. PROTO_READDIR_HANDLER(system__hardware__tpm__keyslots);
  466. PROTO_READDIR_HANDLER(system__hardware__tpm__pcrs);
  467. #endif /* MACFUSE_PROCFS_ENABLE_TPM */
  468. PROTO_READLINK_HANDLER(einval);
  469. PROTO_READLINK_HANDLER(byname__name);
  470. static struct procfs_dispatcher_entry
  471. procfs_link_table[] = {
  472. DECL_LINK(
  473. "/byname/(.+)",
  474. 1,
  475. default_file,
  476. default_file,
  477. byname__name,
  478. byname__name
  479. )
  480. };
  481. static struct procfs_dispatcher_entry
  482. procfs_file_table[] = {
  483. DECL_FILE_WITHFLAGS(
  484. PROCFS_FLAG_ISDOTFILE,
  485. "/system/.*\\._.*|/\\d+/.*\\._.*",
  486. 0,
  487. default_file,
  488. default_file,
  489. default_file_finder_info,
  490. default_file_finder_info
  491. )
  492. DECL_FILE(
  493. "/system/firmware/variables",
  494. 0,
  495. default_file,
  496. default_file,
  497. default_file,
  498. system__firmware__variables
  499. )
  500. DECL_FILE(
  501. "/system/hardware/(lightsensor|motionsensor|mouse)/data",
  502. 1,
  503. default_file,
  504. default_file,
  505. default_file,
  506. system__hardware__xsensor
  507. )
  508. DECL_FILE(
  509. "/system/hardware/camera/screenshot.tiff",
  510. 0,
  511. system__hardware__camera__screenshot,
  512. system__hardware__camera__screenshot,
  513. system__hardware__camera__screenshot,
  514. system__hardware__camera__screenshot
  515. )
  516. DECL_FILE(
  517. "/system/hardware/cpus/(\\d+)/data",
  518. 1,
  519. default_file,
  520. default_file,
  521. default_file,
  522. system__hardware__cpus__cpu__data
  523. )
  524. DECL_FILE(
  525. "/system/hardware/displays/(\\d+)/info",
  526. 1,
  527. default_file,
  528. default_file,
  529. default_file,
  530. system__hardware__displays__display__info
  531. )
  532. DECL_FILE(
  533. "/system/hardware/displays/(\\d+)/screenshot.png",
  534. 1,
  535. system__hardware__displays__display__screenshot,
  536. system__hardware__displays__display__screenshot,
  537. system__hardware__displays__display__screenshot,
  538. system__hardware__displays__display__screenshot
  539. )
  540. #if MACFUSE_PROCFS_ENABLE_TPM
  541. DECL_FILE(
  542. "/system/hardware/tpm/hwmodel",
  543. 0,
  544. default_file,
  545. default_file,
  546. default_file,
  547. system__hardware__tpm__hwmodel
  548. )
  549. DECL_FILE(
  550. "/system/hardware/tpm/hwvendor",
  551. 0,
  552. default_file,
  553. default_file,
  554. default_file,
  555. system__hardware__tpm__hwvendor
  556. )
  557. DECL_FILE(
  558. "/system/hardware/tpm/hwversion",
  559. 0,
  560. default_file,
  561. default_file,
  562. default_file,
  563. system__hardware__tpm__hwversion
  564. )
  565. DECL_FILE(
  566. "/system/hardware/tpm/keyslots/key(\\d+)",
  567. 1,
  568. default_file,
  569. default_file,
  570. system__hardware__tpm__keyslots__slot,
  571. system__hardware__tpm__keyslots__slot
  572. )
  573. DECL_FILE(
  574. "/system/hardware/tpm/pcrs/pcr(\\d+)",
  575. 1,
  576. default_file,
  577. default_file,
  578. system__hardware__tpm__pcrs__pcr,
  579. system__hardware__tpm__pcrs__pcr
  580. )
  581. #endif /* MACFUSE_PROCFS_ENABLE_TPM */
  582. DECL_FILE(
  583. "/(\\d+)/carbon/(name|psn)",
  584. 2,
  585. default_file,
  586. default_file,
  587. default_file,
  588. proc__carbon
  589. )
  590. #if __i386__
  591. DECL_FILE(
  592. "/(\\d+)/fds",
  593. 1,
  594. default_file,
  595. default_file,
  596. default_file,
  597. proc__fds
  598. )
  599. #endif /* __i386__ */
  600. DECL_FILE(
  601. "/(\\d+)/(cmdline|jobc|paddr|pgid|ppid|tdev|tpgid|wchan)",
  602. 2,
  603. default_file,
  604. default_file,
  605. default_file,
  606. proc__generic
  607. )
  608. DECL_FILE(
  609. "/(\\d+)/task/absolutetime_info/(threads_system|threads_user|total_system|total_user)",
  610. 2,
  611. default_file,
  612. default_file,
  613. default_file,
  614. proc__task__absolutetime_info
  615. )
  616. DECL_FILE(
  617. "/(\\d+)/task/basic_info/(policy|resident_size|suspend_count|system_time|user_time|virtual_size)",
  618. 2,
  619. default_file,
  620. default_file,
  621. default_file,
  622. proc__task__basic_info
  623. )
  624. DECL_FILE(
  625. "/(\\d+)/task/events_info/(cow_faults|csw|faults|messages_received|messages_sent|pageins|syscalls_mach|syscalls_unix)",
  626. 2,
  627. default_file,
  628. default_file,
  629. default_file,
  630. proc__task__events_info
  631. )
  632. DECL_FILE(
  633. "/(\\d+)/task/thread_times_info/(system_time|user_time)",
  634. 2,
  635. default_file,
  636. default_file,
  637. default_file,
  638. proc__task__thread_times_info
  639. )
  640. DECL_FILE(
  641. "/(\\d+)/task/mach_name",
  642. 1,
  643. default_file,
  644. default_file,
  645. default_file,
  646. proc__task__mach_name
  647. )
  648. DECL_FILE(
  649. "/(\\d+)/task/ports/([a-f\\d]+)/(msgcount|qlimit|seqno|sorights|task_rights)",
  650. 3,
  651. default_file,
  652. default_file,
  653. default_file,
  654. proc__task__ports__port
  655. )
  656. DECL_FILE(
  657. "/(\\d+)/task/role",
  658. 1,
  659. default_file,
  660. default_file,
  661. default_file,
  662. proc__task__role
  663. )
  664. DECL_FILE(
  665. "/(\\d+)/task/threads/([a-f\\d]+)/basic_info/(cpu_usage|flags|policy|run_state|sleep_time|suspend_count|system_time|user_time)",
  666. 3,
  667. default_file,
  668. default_file,
  669. default_file,
  670. proc__task__threads__thread__basic_info
  671. )
  672. DECL_FILE(
  673. "/(\\d+)/task/threads/([a-f\\d]+)/states/debug/(dr[0-7])",
  674. 3,
  675. default_file,
  676. default_file,
  677. default_file,
  678. proc__task__threads__thread__states__debug
  679. )
  680. DECL_FILE(
  681. "/(\\d+)/task/threads/([a-f\\d]+)/states/exception/(err|faultvaddr|trapno)",
  682. 3,
  683. default_file,
  684. default_file,
  685. default_file,
  686. proc__task__threads__thread__states__exception
  687. )
  688. DECL_FILE(
  689. "/(\\d+)/task/threads/([a-f\\d]+)/states/float/(fpu_fcw|fpu_fsw|fpu_ftw|fpu_fop|fpu_ip|fpu_cs|fpu_dp|fpu_ds|fpu_mxcsr|fpu_mxcsrmask)",
  690. 3,
  691. default_file,
  692. default_file,
  693. default_file,
  694. proc__task__threads__thread__states__float
  695. )
  696. DECL_FILE(
  697. "/(\\d+)/task/threads/([a-f\\d]+)/states/thread/(e[a-d]x|edi|esi|ebp|esp|ss|eflags|eip|[cdefg]s)",
  698. 3,
  699. default_file,
  700. default_file,
  701. default_file,
  702. proc__task__threads__thread__states__thread
  703. )
  704. DECL_FILE(
  705. "/(\\d+)/task/tokens/(audit|security)",
  706. 2,
  707. default_file,
  708. default_file,
  709. default_file,
  710. proc__task__tokens
  711. )
  712. DECL_FILE(
  713. "/(\\d+)/task/vmmap",
  714. 1,
  715. default_file,
  716. default_file,
  717. default_file,
  718. proc__task__vmmap
  719. )
  720. DECL_FILE(
  721. "/(\\d+)/task/vmmap_r",
  722. 1,
  723. default_file,
  724. default_file,
  725. default_file,
  726. proc__task__vmmap_r
  727. )
  728. DECL_FILE(
  729. "/(\\d+)/windows/(all|onscreen)",
  730. 2,
  731. default_file,
  732. default_file,
  733. default_file,
  734. proc__windows__generic
  735. )
  736. DECL_FILE(
  737. "/(\\d+)/windows/identify",
  738. 1,
  739. proc__windows__identify,
  740. proc__windows__identify,
  741. default_file,
  742. zero
  743. )
  744. DECL_FILE(
  745. "/(\\d+)/windows/screenshots/([a-f\\d]+).png",
  746. 2,
  747. proc__windows__screenshots__window,
  748. proc__windows__screenshots__window,
  749. proc__windows__screenshots__window,
  750. proc__windows__screenshots__window
  751. )
  752. DECL_FILE(
  753. "/(\\d+)/(ucred|pcred)/(groups|rgid|ruid|svgid|svuid|uid)",
  754. 3,
  755. default_file,
  756. default_file,
  757. default_file,
  758. proc__xcred
  759. )
  760. };
  761. static struct procfs_dispatcher_entry
  762. procfs_directory_table[] = {
  763. DECL_DIRECTORY(
  764. "/",
  765. 0,
  766. default_directory,
  767. default_directory,
  768. default_directory,
  769. root,
  770. { NULL },
  771. { "byname", "system", NULL }
  772. )
  773. DECL_DIRECTORY(
  774. "/byname",
  775. 0,
  776. default_directory,
  777. default_directory,
  778. default_directory,
  779. byname,
  780. { NULL },
  781. { NULL }
  782. )
  783. DECL_DIRECTORY_COMPACT(
  784. "/system",
  785. { NULL },
  786. { "firmware", "hardware", NULL },
  787. )
  788. DECL_DIRECTORY_COMPACT(
  789. "/system/firmware",
  790. { "variables", NULL },
  791. { NULL }
  792. )
  793. DECL_DIRECTORY_COMPACT(
  794. "/system/hardware",
  795. { NULL },
  796. #if MACFUSE_PROCFS_ENABLE_TPM
  797. {
  798. "camera", "cpus", "displays", "lightsensor", "motionsensor",
  799. "mouse", "tpm", NULL
  800. }
  801. #else
  802. {
  803. "camera", "cpus", "displays", "lightsensor", "motionsensor",
  804. "mouse", NULL
  805. }
  806. #endif /* MACFUSE_PROCFS_ENABLE_TPM */
  807. )
  808. DECL_DIRECTORY_COMPACT(
  809. "/system/hardware/camera",
  810. { "screenshot.tiff", NULL },
  811. { NULL },
  812. )
  813. DECL_DIRECTORY(
  814. "/system/hardware/cpus",
  815. 0,
  816. default_directory,
  817. default_directory,
  818. default_directory,
  819. system__hardware__cpus,
  820. { NULL },
  821. { NULL },
  822. )
  823. DECL_DIRECTORY(
  824. "/system/hardware/cpus/(\\d+)",
  825. 1,
  826. default_directory,
  827. default_directory,
  828. default_directory,
  829. system__hardware__cpus__cpu,
  830. { "data", NULL },
  831. { NULL },
  832. )
  833. DECL_DIRECTORY(
  834. "/system/hardware/displays",
  835. 0,
  836. default_directory,
  837. default_directory,
  838. default_directory,
  839. system__hardware__displays,
  840. { NULL },
  841. { NULL },
  842. )
  843. DECL_DIRECTORY(
  844. "/system/hardware/displays/(\\d+)",
  845. 1,
  846. default_directory,
  847. default_directory,
  848. system__hardware__displays__display,
  849. system__hardware__displays__display,
  850. { "info", "screenshot.png", NULL },
  851. { NULL },
  852. )
  853. DECL_DIRECTORY_COMPACT(
  854. "/system/hardware/lightsensor",
  855. { "data", NULL },
  856. { NULL },
  857. )
  858. DECL_DIRECTORY_COMPACT(
  859. "/system/hardware/motionsensor",
  860. { "data", NULL },
  861. { NULL },
  862. )
  863. DECL_DIRECTORY_COMPACT(
  864. "/system/hardware/mouse",
  865. { "data", NULL },
  866. { NULL },
  867. )
  868. #if MACFUSE_PROCFS_ENABLE_TPM
  869. DECL_DIRECTORY_COMPACT(
  870. "/system/hardware/tpm",
  871. { "hwmodel", "hwvendor", "hwversion", NULL },
  872. { "keyslots", "pcrs" }
  873. )
  874. DECL_DIRECTORY(
  875. "/system/hardware/tpm/keyslots",
  876. 0,
  877. default_directory,
  878. default_directory,
  879. default_directory,
  880. system__hardware__tpm__keyslots,
  881. { NULL },
  882. { NULL },
  883. )
  884. DECL_DIRECTORY(
  885. "/system/hardware/tpm/pcrs",
  886. 0,
  887. default_directory,
  888. default_directory,
  889. default_directory,
  890. system__hardware__tpm__pcrs,
  891. { NULL },
  892. { NULL },
  893. )
  894. #endif /* MACFUSE_PROCFS_ENABLE_TPM */
  895. DECL_DIRECTORY_COMPACT(
  896. "/\\d+",
  897. {
  898. "cmdline",
  899. #if __i386__
  900. "fds",
  901. #endif /* __i386__ */
  902. "jobc", "paddr", "pgid", "ppid", "tdev", "tpgid",
  903. "wchan", "windows", NULL
  904. },
  905. { "carbon", "pcred", "task", "ucred", NULL }
  906. )
  907. DECL_DIRECTORY_COMPACT(
  908. "/\\d+/carbon",
  909. { "name", "psn", NULL },
  910. { NULL }
  911. )
  912. DECL_DIRECTORY_COMPACT(
  913. "/\\d+/pcred",
  914. { "rgid", "ruid", "svgid", "svgid", NULL },
  915. { NULL }
  916. )
  917. DECL_DIRECTORY_COMPACT(
  918. "/\\d+/task",
  919. { "mach_name", "role", "vmmap", "vmmap_r", NULL },
  920. {
  921. "absolutetime_info", "basic_info", "events_info", "ports",
  922. "thread_times_info", "threads", "tokens", NULL
  923. }
  924. )
  925. DECL_DIRECTORY_COMPACT(
  926. "/\\d+/task/absolutetime_info",
  927. {
  928. "threads_system", "threads_user", "total_system",
  929. "total_user", NULL
  930. },
  931. { NULL }
  932. )
  933. DECL_DIRECTORY_COMPACT(
  934. "/\\d+/task/basic_info",
  935. {
  936. "policy", "resident_size", "suspend_count", "system_time",
  937. "user_time", "virtual_size", NULL
  938. },
  939. { NULL }
  940. )
  941. DECL_DIRECTORY_COMPACT(
  942. "/\\d+/task/events_info",
  943. {
  944. "cow_faults", "csw", "faults", "messages_received",
  945. "messages_sent", "pageins", "syscalls_mach", "syscalls_unix", NULL
  946. },
  947. { NULL }
  948. )
  949. DECL_DIRECTORY(
  950. "/(\\d+)/task/ports",
  951. 1,
  952. default_directory,
  953. default_directory,
  954. default_directory,
  955. proc__task__ports,
  956. { NULL },
  957. { NULL }
  958. )
  959. DECL_DIRECTORY(
  960. "/(\\d+)/task/ports/([a-f\\d]+)",
  961. 2,
  962. default_directory,
  963. default_directory,
  964. proc__task__ports__port,
  965. default,
  966. { "msgcount", "qlimit", "seqno", "sorights", "task_rights", NULL },
  967. { NULL }
  968. )
  969. DECL_DIRECTORY_COMPACT(
  970. "/\\d+/task/thread_times_info",
  971. { "system_time", "user_time", NULL },
  972. { NULL }
  973. )
  974. DECL_DIRECTORY(
  975. "/(\\d+)/task/threads",
  976. 1,
  977. default_directory,
  978. default_directory,
  979. default_directory,
  980. proc__task__threads,
  981. { NULL },
  982. { NULL }
  983. )
  984. DECL_DIRECTORY(
  985. "/(\\d+)/task/threads/([a-f\\d])+",
  986. 2,
  987. default_directory,
  988. default_directory,
  989. proc__task__threads__thread,
  990. default,
  991. { NULL },
  992. { "basic_info", "states", NULL }
  993. )
  994. DECL_DIRECTORY_COMPACT(
  995. "/\\d+/task/threads/[a-f\\d]+/basic_info",
  996. {
  997. "cpu_usage", "flags", "policy", "run_state", "sleep_time",
  998. "suspend_count", "system_time", "user_time", NULL
  999. },
  1000. { NULL }
  1001. )
  1002. DECL_DIRECTORY_COMPACT(
  1003. "/\\d+/task/threads/[a-f\\d]+/states",
  1004. { "debug", "exception", "float", "thread", NULL },
  1005. { NULL }
  1006. )
  1007. DECL_DIRECTORY_COMPACT(
  1008. "/\\d+/task/threads/[a-f\\d]+/states/debug",
  1009. { "dr0", "dr1", "dr2", "dr3", "dr4", "dr5", "dr6", "dr7", NULL },
  1010. { NULL }
  1011. )
  1012. DECL_DIRECTORY_COMPACT(
  1013. "/\\d+/task/threads/[a-f\\d]+/states/exception",
  1014. { "err", "faultvaddr", "trapno", NULL },
  1015. { NULL }
  1016. )
  1017. DECL_DIRECTORY_COMPACT(
  1018. "/\\d+/task/threads/[a-f\\d]+/states/float",
  1019. {
  1020. "fpu_cs", "fpu_dp", "fpu_ds", "fpu_fcw", "fpu_fop", "fpu_fsw",
  1021. "fpu_ftw", "fpu_ip", "fpu_mxcsr", "fpu_mxcsrmask", NULL
  1022. },
  1023. { NULL }
  1024. )
  1025. DECL_DIRECTORY_COMPACT(
  1026. "/\\d+/task/threads/[a-f\\d]+/states/thread",
  1027. {
  1028. "eax", "ebx", "ecx", "edx", "edi", "esi", "ebp", "esp", "ss",
  1029. "eflags", "eip", "cs", "ds", "es", "fs", "gs", NULL
  1030. },
  1031. { NULL }
  1032. )
  1033. DECL_DIRECTORY_COMPACT(
  1034. "/\\d+/task/tokens",
  1035. { "audit", "security", NULL },
  1036. { NULL }
  1037. )
  1038. DECL_DIRECTORY_COMPACT(
  1039. "/\\d+/ucred",
  1040. { "groups", "uid", NULL },
  1041. { NULL }
  1042. )
  1043. DECL_DIRECTORY_COMPACT(
  1044. "/\\d+/windows",
  1045. { "all", "onscreen", "identify", NULL },
  1046. { "screenshots", NULL }
  1047. )
  1048. DECL_DIRECTORY(
  1049. "/(\\d+)/windows/screenshots",
  1050. 1,
  1051. default_directory,
  1052. default_directory,
  1053. default_directory,
  1054. proc__windows__screenshots,
  1055. { NULL },
  1056. { NULL },
  1057. )
  1058. };
  1059. // BEGIN: OPEN/OPENDIR
  1060. //
  1061. // int
  1062. // procfs_open/opendir_<handler>(procfs_dispatcher_entry_t e,
  1063. // const char *argv[],
  1064. // const char *path,
  1065. // struct fuse_file_info *fi)
  1066. OPEN_HANDLER(default_file)
  1067. {
  1068. return 0;
  1069. }
  1070. OPEN_HANDLER(eisdir)
  1071. {
  1072. return -EISDIR;
  1073. }
  1074. OPEN_HANDLER(proc__windows__identify)
  1075. {
  1076. if (fi->fh != 0) { /* XXX: need locking */
  1077. return 0;
  1078. } else {
  1079. fi->fh = 1;
  1080. }
  1081. char *whandler = NULL;
  1082. if ((whandler = getenv("MACFUSE_PROCFS_WHANDLER")) == NULL) {
  1083. goto bail;
  1084. }
  1085. int npid = vfork();
  1086. if (npid == 0) {
  1087. execl(whandler, whandler, argv[0], NULL);
  1088. return 0;
  1089. }
  1090. bail:
  1091. return 0;
  1092. }
  1093. OPEN_HANDLER(proc__windows__screenshots__window)
  1094. {
  1095. if (fi->fh != 0) { /* XXX: need locking */
  1096. return 0;
  1097. }
  1098. pid_t pid = strtol(argv[0], NULL, 10);
  1099. CGWindowID target = strtol(argv[1], NULL, 16);
  1100. ProcessSerialNumber psn;
  1101. OSStatus status = GetProcessForPID(pid, &psn);
  1102. if (status != noErr) {
  1103. return -ENOENT;
  1104. }
  1105. CGSConnectionID conn;
  1106. CGError err = CGSGetConnectionIDForPSN(0, &psn, &conn);
  1107. if (err != kCGErrorSuccess) {
  1108. return -ENOENT;
  1109. }
  1110. #define MAX_WINDOWS 256
  1111. CGSWindowID windowIDs[MAX_WINDOWS];
  1112. int windowCount = 0;
  1113. int i = 0;
  1114. err = CGSGetWindowList(_CGSDefaultConnection(), conn, MAX_WINDOWS,
  1115. windowIDs, &windowCount);
  1116. for (i = 0; i < windowCount; i++) {
  1117. if (windowIDs[i] == target) {
  1118. goto doread;
  1119. }
  1120. }
  1121. return -ENOENT;
  1122. doread:
  1123. CFMutableDataRef window_png = (CFMutableDataRef)0;
  1124. int ret = PROCFS_GetPNGForWindowAtIndex(target, &window_png);
  1125. if (ret == -1) {
  1126. return -EIO;
  1127. }
  1128. struct ProcfsWindowData *pwd =
  1129. (struct ProcfsWindowData *)malloc(sizeof(struct ProcfsWindowData));
  1130. if (!pwd) {
  1131. CFRelease(window_png);
  1132. return -ENOMEM;
  1133. }
  1134. pwd->window_png = window_png;
  1135. pwd->max_len = PROCFS_GetPNGSizeForWindowAtIndex(target);
  1136. pwd->len = (size_t)CFDataGetLength(window_png);
  1137. fi->fh = (uint64_t)pwd;
  1138. return 0;
  1139. }
  1140. OPEN_HANDLER(system__hardware__camera__screenshot)
  1141. {
  1142. pthread_mutex_lock(&camera_lock);
  1143. if (camera_busy) {
  1144. pthread_mutex_unlock(&camera_lock);
  1145. return -EBUSY;
  1146. } else {
  1147. camera_busy = 1;
  1148. pthread_mutex_unlock(&camera_lock);
  1149. }
  1150. int ret = PROCFS_GetTIFFFromCamera(&camera_tiff);
  1151. return ret;
  1152. }
  1153. OPEN_HANDLER(system__hardware__displays__display__screenshot)
  1154. {
  1155. pthread_mutex_lock(&display_lock);
  1156. if (display_busy) {
  1157. pthread_mutex_unlock(&display_lock);
  1158. return -EBUSY;
  1159. } else {
  1160. display_busy = 1;
  1161. pthread_mutex_unlock(&display_lock);
  1162. }
  1163. unsigned long index = strtol(argv[0], NULL, 10);
  1164. CGDisplayCount display_count = PROCFS_GetDisplayCount();
  1165. if (index >= display_count) {
  1166. return -ENOENT;
  1167. }
  1168. if (display_png) {
  1169. CFRelease(display_png);
  1170. display_png = (CFMutableDataRef)0;
  1171. }
  1172. int ret = PROCFS_GetPNGForDisplayAtIndex(index, &display_png);
  1173. if (ret) {
  1174. if (display_png) {
  1175. CFRelease(display_png);
  1176. display_png = (CFMutableDataRef)0;
  1177. }
  1178. return -EIO;
  1179. }
  1180. return 0;
  1181. }
  1182. OPENDIR_HANDLER(default_directory)
  1183. {
  1184. return 0;
  1185. }
  1186. OPENDIR_HANDLER(enotdir)
  1187. {
  1188. return -ENOTDIR;
  1189. }
  1190. // END: OPEN/OPENDIR
  1191. // BEGIN: RELEASE/RELEASEDIR
  1192. //
  1193. // int
  1194. // procfs_release/releasedir_<handler>(procfs_dispatcher_entry_t e,
  1195. // const char *argv[],
  1196. // const char *path,
  1197. // struct fuse_file_info *fi)
  1198. RELEASE_HANDLER(default_file)
  1199. {
  1200. return 0;
  1201. }
  1202. RELEASE_HANDLER(eisdir)
  1203. {
  1204. return -EISDIR;
  1205. }
  1206. RELEASE_HANDLER(proc__windows__identify)
  1207. {
  1208. fi->fh = 0;
  1209. return 0;
  1210. }
  1211. RELEASE_HANDLER(proc__windows__screenshots__window)
  1212. {
  1213. if (fi->fh) {
  1214. struct ProcfsWindowData *pwd = (struct ProcfsWindowData *)(fi->fh);
  1215. CFRelease((CFMutableDataRef)(pwd->window_png));
  1216. free((void *)pwd);
  1217. fi->fh = 0;
  1218. }
  1219. return 0;
  1220. }
  1221. RELEASE_HANDLER(system__hardware__camera__screenshot)
  1222. {
  1223. pthread_mutex_lock(&camera_lock);
  1224. camera_busy = 0;
  1225. pthread_mutex_unlock(&camera_lock);
  1226. return 0;
  1227. }
  1228. RELEASE_HANDLER(system__hardware__displays__display__screenshot)
  1229. {
  1230. pthread_mutex_lock(&display_lock);
  1231. display_busy = 0;
  1232. if (display_png) {
  1233. CFRelease(display_png);
  1234. display_png = (CFMutableDataRef)0;
  1235. }
  1236. pthread_mutex_unlock(&display_lock);
  1237. return 0;
  1238. }
  1239. RELEASEDIR_HANDLER(default_directory)
  1240. {
  1241. return 0;
  1242. }
  1243. RELEASEDIR_HANDLER(enotdir)
  1244. {
  1245. return -ENOTDIR;
  1246. }
  1247. // END: RELEASE/RELEASEDIR
  1248. // BEGIN: GETATTR
  1249. //
  1250. // int
  1251. // procfs_getattr_<handler>(procfs_dispatcher_entry_t e,
  1252. // const char *argv[],
  1253. // struct stat *stbuf)
  1254. GETATTR_HANDLER(default_file)
  1255. {
  1256. time_t current_time = time(NULL);
  1257. stbuf->st_mode = S_IFREG | 0444;
  1258. stbuf->st_nlink = 1;
  1259. stbuf->st_size = 0;
  1260. if (procfs_ui) {
  1261. stbuf->st_size = PROCFS_DEFAULT_FILE_SIZE;
  1262. }
  1263. stbuf->st_atime = stbuf->st_ctime = stbuf->st_mtime = current_time;
  1264. return 0;
  1265. }
  1266. GETATTR_HANDLER(default_file_finder_info)
  1267. {
  1268. if (!procfs_ui) {
  1269. return -ENOENT;
  1270. }
  1271. time_t current_time = time(NULL);
  1272. stbuf->st_mode = S_IFREG | 0444;
  1273. stbuf->st_nlink = 1;
  1274. stbuf->st_size = 82;
  1275. stbuf->st_atime = stbuf->st_ctime = stbuf->st_mtime = current_time;
  1276. return 0;
  1277. }
  1278. GETATTR_HANDLER(default_directory)
  1279. {
  1280. time_t current_time = time(NULL);
  1281. stbuf->st_mode = S_IFDIR | 0555;
  1282. stbuf->st_nlink = 1;
  1283. stbuf->st_size = 0;
  1284. stbuf->st_atime = stbuf->st_ctime = stbuf->st_mtime = current_time;
  1285. return 0;
  1286. }
  1287. GETATTR_HANDLER(default_link)
  1288. {
  1289. stbuf->st_mode = S_IFLNK | 0755;
  1290. stbuf->st_nlink = 1;
  1291. stbuf->st_size = 0;
  1292. return 0;
  1293. }
  1294. GETATTR_HANDLER(byname__name)
  1295. {
  1296. const char *target_Pname = argv[0];
  1297. struct stat the_stat;
  1298. char the_name[MAXNAMLEN + 1];
  1299. Boolean strstatus = false;
  1300. ProcessSerialNumber psn;
  1301. OSErr osErr = noErr;
  1302. OSStatus status;
  1303. CFStringRef Pname;
  1304. pid_t Pid;
  1305. psn.highLongOfPSN = kNoProcess;
  1306. psn.lowLongOfPSN = kNoProcess;
  1307. while ((osErr = GetNextProcess(&psn)) != procNotFound) {
  1308. status = GetProcessPID(&psn, &Pid);
  1309. if (status != noErr) {
  1310. continue;
  1311. }
  1312. Pname = (CFStringRef)0;
  1313. status = CopyProcessName(&psn, &Pname);
  1314. if (status != noErr) {
  1315. if (Pname) {
  1316. CFRelease(Pname);
  1317. Pname = (CFStringRef)0;
  1318. }
  1319. continue;
  1320. }
  1321. strstatus = CFStringGetCString(Pname, the_name, MAXNAMLEN,
  1322. kCFStringEncodingASCII);
  1323. if (strstatus != true) {
  1324. Pid = 0;
  1325. } else if (strcmp(target_Pname, the_name) != 0) {
  1326. Pid = 0;
  1327. }
  1328. CFRelease(Pname);
  1329. Pname = (CFStringRef)0;
  1330. if (Pid) {
  1331. break;
  1332. }
  1333. }
  1334. if (!Pid) {
  1335. return -ENOENT;
  1336. }
  1337. time_t current_time = time(NULL);
  1338. stbuf->st_mode = S_IFLNK | 0755;
  1339. stbuf->st_nlink = 1;
  1340. stbuf->st_atime = stbuf->st_ctime = stbuf->st_mtime = current_time;
  1341. int len = snprintf(the_name, MAXNAMLEN, "../%u", Pid);
  1342. the_stat.st_size = len;
  1343. return 0;
  1344. }
  1345. GETATTR_HANDLER(system__hardware__displays__display)
  1346. {
  1347. unsigned long index = strtol(argv[0], NULL, 10);
  1348. CGDisplayCount display_count = PROCFS_GetDisplayCount();
  1349. if (index >= display_count) {
  1350. return -ENOENT;
  1351. }
  1352. time_t current_time = time(NULL);
  1353. stbuf->st_mode = S_IFDIR | 0555;
  1354. stbuf->st_nlink = 1;
  1355. stbuf->st_size = 0;
  1356. stbuf->st_atime = stbuf->st_ctime = stbuf->st_mtime = current_time;
  1357. return 0;
  1358. }
  1359. GETATTR_HANDLER(system__hardware__camera__screenshot)
  1360. {
  1361. time_t current_time = time(NULL);
  1362. stbuf->st_mode = S_IFREG | 0444;
  1363. stbuf->st_nlink = 1;
  1364. stbuf->st_atime = stbuf->st_ctime = stbuf->st_mtime = current_time;
  1365. stbuf->st_size = PROCFS_GetTIFFSizeFromCamera();
  1366. return 0;
  1367. }
  1368. GETATTR_HANDLER(system__hardware__displays__display__screenshot)
  1369. {
  1370. unsigned long index = strtol(argv[0], NULL, 10);
  1371. time_t current_time = time(NULL);
  1372. stbuf->st_mode = S_IFREG | 0444;
  1373. stbuf->st_nlink = 1;
  1374. stbuf->st_atime = stbuf->st_ctime = stbuf->st_mtime = current_time;
  1375. stbuf->st_size = PROCFS_GetPNGSizeForDisplayAtIndex(index);
  1376. return 0;
  1377. }
  1378. #if MACFUSE_PROCFS_ENABLE_TPM
  1379. GETATTR_HANDLER(system__hardware__tpm__keyslots__slot)
  1380. {
  1381. uint32_t keys[256];
  1382. unsigned long slotno = strtol(argv[0], NULL, 10);
  1383. uint16_t slots_used = 0;
  1384. uint32_t slots_free = 0;
  1385. uint32_t slots_total = 0;
  1386. if (TPM_GetCapability_Slots(&slots_free)) {
  1387. return -ENOENT;
  1388. }
  1389. if (TPM_GetCapability_Key_Handle(&slots_used, keys)) {
  1390. return -ENOENT;
  1391. }
  1392. slots_total = slots_used + slots_free;
  1393. if (slotno >= slots_total) {
  1394. return -ENOENT;
  1395. }
  1396. time_t current_time = time(NULL);
  1397. stbuf->st_nlink = 1;
  1398. stbuf->st_size = 9;
  1399. stbuf->st_atime = stbuf->st_ctime = stbuf->st_mtime = current_time;
  1400. if (slotno >= slots_used) {
  1401. stbuf->st_mode = S_IFREG | 0000;
  1402. } else {
  1403. stbuf->st_mode = S_IFREG | 0444;
  1404. }
  1405. return 0;
  1406. }
  1407. GETATTR_HANDLER(system__hardware__tpm__pcrs__pcr)
  1408. {
  1409. time_t current_time = time(NULL);
  1410. stbuf->st_mode = S_IFREG | 0444;
  1411. stbuf->st_nlink = 1;
  1412. stbuf->st_size = 60;
  1413. stbuf->st_atime = stbuf->st_ctime = stbuf->st_mtime = current_time;
  1414. return 0;
  1415. }
  1416. #endif /* MACFUSE_PROCFS_ENABLE_TPM */
  1417. GETATTR_HANDLER(proc__task__ports__port)
  1418. {
  1419. kern_return_t kr;
  1420. task_t the_task = MACH_PORT_NULL;
  1421. pid_t pid = strtol(argv[0], NULL, 10);
  1422. kr = task_for_pid(mach_task_self(), pid, &the_task);
  1423. if (kr != KERN_SUCCESS) {
  1424. return -ENOENT;
  1425. }
  1426. DECL_PORT_LIST();
  1427. INIT_PORT_LIST(the_task);
  1428. int found = 0;
  1429. unsigned int i;
  1430. unsigned int the_port_name = strtoul(argv[1], NULL, 16);
  1431. for (i = 0; i < name_count; i++) {
  1432. if (the_port_name == name_list[i]) {
  1433. found = 1;
  1434. break;
  1435. }
  1436. }
  1437. FINI_PORT_LIST();
  1438. if (the_task != MACH_PORT_NULL) {
  1439. mach_port_deallocate(mach_task_self(), the_task);
  1440. }
  1441. if (!found) {
  1442. return -ENOENT;
  1443. }
  1444. time_t current_time = time(NULL);
  1445. stbuf->st_mode = S_IFDIR | 0555;
  1446. stbuf->st_nlink = 1;
  1447. stbuf->st_size = 0;
  1448. stbuf->st_atime = stbuf->st_ctime = stbuf->st_mtime = current_time;
  1449. return 0;
  1450. }
  1451. GETATTR_HANDLER(proc__task__threads__thread)
  1452. {
  1453. kern_return_t kr;
  1454. task_t the_task = MACH_PORT_NULL;
  1455. pid_t pid = strtol(argv[0], NULL, 10);
  1456. kr = task_for_pid(mach_task_self(), pid, &the_task);
  1457. if (kr != KERN_SUCCESS) {
  1458. return -ENOENT;
  1459. }
  1460. DECL_THREAD_LIST();
  1461. INIT_THREAD_LIST(the_task);
  1462. FINI_THREAD_LIST();
  1463. if (the_task != MACH_PORT_NULL) {
  1464. mach_port_deallocate(mach_task_self(), the_task);
  1465. }
  1466. unsigned int the_thread_name = strtoul(argv[1], NULL, 16);
  1467. if (the_thread_name >= thread_count) {
  1468. return -ENOENT;
  1469. }
  1470. time_t current_time = time(NULL);
  1471. stbuf->st_mode = S_IFDIR | 0555;
  1472. stbuf->st_nlink = 1;
  1473. stbuf->st_size = 0;
  1474. stbuf->st_atime = stbuf->st_ctime = stbuf->st_mtime = current_time;
  1475. return 0;
  1476. }
  1477. GETATTR_HANDLER(proc__windows__screenshots__window)
  1478. {
  1479. pid_t pid = strtol(argv[0], NULL, 10);
  1480. CGWindowID target = strtol(argv[1], NULL, 16);
  1481. ProcessSerialNumber psn;
  1482. OSStatus status = GetProcessForPID(pid, &psn);
  1483. if (status != noErr) {
  1484. return 0; /* technically not an error in this case */
  1485. }
  1486. CGSConnectionID conn;
  1487. CGError err = CGSGetConnectionIDForPSN(0, &psn, &conn);
  1488. if (err != kCGErrorSuccess) {
  1489. return 0; /* just be nice */
  1490. }
  1491. #define MAX_WINDOWS 256
  1492. CGSWindowID windowIDs[MAX_WINDOWS];
  1493. int windowCount = 0;
  1494. int i = 0;
  1495. err = CGSGetWindowList(_CGSDefaultConnection(), conn, MAX_WINDOWS,
  1496. windowIDs, &windowCount);
  1497. for (i = 0; i < windowCount; i++) {
  1498. if (windowIDs[i] == target) {
  1499. time_t current_time = time(NULL);
  1500. stbuf->st_mode = S_IFREG | 0444;
  1501. stbuf->st_nlink = 1;
  1502. stbuf->st_atime = stbuf->st_ctime = stbuf->st_mtime = current_time;
  1503. stbuf->st_size = PROCFS_GetPNGSizeForWindowAtIndex(windowIDs[i]);
  1504. return 0;
  1505. }
  1506. }
  1507. return -ENOENT;
  1508. }
  1509. // END: GETATTR
  1510. #include <stdio.h>
  1511. #include <stdlib.h>
  1512. #include <string.h>
  1513. #include <libgen.h>
  1514. #include <sys/sysctl.h>
  1515. int
  1516. procinfo(pid_t pid, struct kinfo_proc *kp)
  1517. {
  1518. int mib[4];
  1519. size_t bufsize = 0, orig_bufsize = 0;
  1520. struct kinfo_proc *kprocbuf;
  1521. int retry_count = 0;
  1522. int local_error;
  1523. mib[0] = CTL_KERN;
  1524. mib[1] = KERN_PROC;
  1525. mib[2] = KERN_PROC_PID;
  1526. mib[3] = pid;
  1527. kprocbuf = kp;
  1528. orig_bufsize = bufsize = sizeof(struct kinfo_proc);
  1529. for (retry_count = 0; ; retry_count++) {
  1530. local_error = 0;
  1531. bufsize = orig_bufsize;
  1532. if ((local_error = sysctl(mib, 4, kp, &bufsize, NULL, 0)) < 0) {
  1533. if (retry_count < 1000) {
  1534. sleep(1);
  1535. continue;
  1536. }
  1537. return local_error;
  1538. } else if (local_error == 0) {
  1539. br