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.

189 lines
4.2KB

  1. #include <stdint.h>
  2. #include <unistd.h>
  3. #include <stdlib.h>
  4. #include <signal.h>
  5. #include <syslog.h>
  6. #include <errno.h>
  7. #include <ev.h>
  8. #include "log.h"
  9. #include "core.h"
  10. #define DEFAULT_AWDL_DEVICE "awdl0"
  11. #define FAILED_DUMP "failed.pcap"
  12. static void daemonize() {
  13. pid_t pid;
  14. long x;
  15. /* Fork off the parent process */
  16. pid = fork();
  17. /* An error occurred */
  18. if (pid < 0)
  19. exit(EXIT_FAILURE);
  20. /* Success: Let the parent terminate */
  21. if (pid > 0)
  22. exit(EXIT_SUCCESS);
  23. /* On success: The child process becomes session leader */
  24. if (setsid() < 0)
  25. exit(EXIT_FAILURE);
  26. /* Catch, ignore and handle signals */
  27. /* TODO: Implement a working signal handler */
  28. signal(SIGCHLD, SIG_IGN);
  29. signal(SIGHUP, SIG_IGN);
  30. /* Fork off for the second time*/
  31. pid = fork();
  32. /* An error occurred */
  33. if (pid < 0)
  34. exit(EXIT_FAILURE);
  35. /* Success: Let the parent terminate */
  36. if (pid > 0)
  37. exit(EXIT_SUCCESS);
  38. /* Set new file permissions */
  39. umask(0);
  40. /* Change the working directory to the root directory */
  41. /* or another appropriated directory */
  42. chdir("/");
  43. /* Close all open file descriptors */
  44. for (x = sysconf(_SC_OPEN_MAX); x >= 0; x--) {
  45. close(x);
  46. }
  47. /* Open the log file */
  48. openlog("owl", LOG_PID, LOG_DAEMON);
  49. }
  50. int main(int argc, char *argv[]) {
  51. int c;
  52. int daemon = 0;
  53. int dump = 0;
  54. int chan_num = 6;
  55. struct awdl_chan chan;
  56. int log_level = LOG_INFO;
  57. int filter_rssi = 1;
  58. int no_monitor_mode = 0;
  59. char wlan[IFNAMSIZ];
  60. char host[IFNAMSIZ] = DEFAULT_AWDL_DEVICE;
  61. struct ev_loop *loop;
  62. struct daemon_state state;
  63. while ((c = getopt(argc, argv, "Dc:dvi:h:a:t:fN")) != -1) {
  64. switch (c) {
  65. case 'D':
  66. daemon = 1;
  67. break;
  68. case 'c':
  69. chan_num = atoi(optarg);
  70. break;
  71. case 'd':
  72. dump = 1;
  73. break;
  74. case 'f':
  75. filter_rssi = 0;
  76. break;
  77. case 'v':
  78. if (log_level < LOG_TRACE)
  79. log_level++; /* increase log level with every occurence of option */
  80. break;
  81. case 'i':
  82. strcpy(wlan, optarg);
  83. break;
  84. case 'h':
  85. strcpy(host, optarg);
  86. break;
  87. case 'N':
  88. no_monitor_mode = 1;
  89. break;
  90. case '?':
  91. if (optopt == 'i')
  92. fprintf(stderr, "Option -%c needs to specify a wireless interface.\n", optopt);
  93. return EXIT_FAILURE;
  94. default:
  95. abort();
  96. }
  97. }
  98. log_set_level(log_level);
  99. printf(" .oOXWMMMMWXOx:\n"
  100. " .oOOOx:'''''''''''':OOOx:\n"
  101. " oXOo' ........ ':OXx.\n"
  102. " .oOOO''''''''''OOOo.\n"
  103. " oXOo' 'oOO:\n"
  104. " :oOOOOXXXXOOOOo:.\n"
  105. " oXO:' ':OXo\n"
  106. " .:xOXXXXXXOx:.\n"
  107. " .xXMMMMMMMMMMMMMMMMXx.\n"
  108. " 'XWWWWWWMMMMMMMMMMMMMMMMMMMMMMWWWWWWX'\n"
  109. " oWMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMWo\n"
  110. " OMMMMMMWWMMMMMMMMMMMMMMWWWMMMMMO\n"
  111. " OMMWx' 'xWMMMMWx' 'oXMMO\n"
  112. " :MW: oMMx 'WM:\n"
  113. " XM' .xOOo. :o .xOOo. WX\n"
  114. " WX :MMMMMX :MMMMMX xW\n"
  115. " XW 'WMMMMX .xx. 'WMMMWX XX\n"
  116. " 'Wx 'xWMx' OMMO 'xWMx' xM'\n"
  117. " 'XX: 'XX' :XX'\n"
  118. " 'xXOx:..................:xXWx'\n"
  119. " 'xXMMMMMMMMMMMMMMMMMMWO'\n"
  120. "\n"
  121. " Open Wireless Link\n"
  122. "\n"
  123. " https://owlink.org\n"
  124. "\n");
  125. if (daemon)
  126. daemonize();
  127. switch (chan_num) {
  128. case 6:
  129. chan = CHAN_OPCLASS_6;
  130. break;
  131. case 44:
  132. chan = CHAN_OPCLASS_44;
  133. break;
  134. case 149:
  135. chan = CHAN_OPCLASS_149;
  136. break;
  137. default:
  138. log_error("Unsupported channel %d (use 6, 44, or 149)", chan_num);
  139. return EXIT_FAILURE;
  140. }
  141. state.io.wlan_no_monitor_mode = no_monitor_mode;
  142. if (awdl_init(&state, wlan, host, chan, dump ? FAILED_DUMP : 0) < 0) {
  143. log_error("could not initialize core");
  144. return EXIT_FAILURE;
  145. }
  146. state.awdl_state.filter_rssi = filter_rssi;
  147. if (state.io.wlan_ifindex)
  148. log_info("WLAN device: %s (addr %s)", state.io.wlan_ifname, ether_ntoa(&state.io.if_ether_addr));
  149. if (state.io.host_ifindex)
  150. log_info("Host device: %s", state.io.host_ifname);
  151. loop = EV_DEFAULT;
  152. awdl_schedule(loop, &state);
  153. ev_run(loop, 0);
  154. awdl_free(&state);
  155. return EXIT_SUCCESS;
  156. }