PageRenderTime 72ms CodeModel.GetById 29ms RepoModel.GetById 1ms app.codeStats 0ms

/TeXmacs-1.0.7.11-src/src/System/Link/tm_link.cpp

#
C++ | 100 lines | 74 code | 11 blank | 15 comment | 36 complexity | 81f09c543c8206c3d848af39bc420394 MD5 | raw file
Possible License(s): GPL-3.0, GPL-2.0, MPL-2.0-no-copyleft-exception
  1. /******************************************************************************
  2. * MODULE : tm_link.cpp
  3. * DESCRIPTION: Links between TeXmacs and extern programs
  4. * COPYRIGHT : (C) 2007 Joris van der Hoeven
  5. *******************************************************************************
  6. * This software falls under the GNU general public license version 3 or later.
  7. * It comes WITHOUT ANY WARRANTY WHATSOEVER. For details, see the file LICENSE
  8. * in the root directory or <http://www.gnu.org/licenses/gpl-3.0.html>.
  9. ******************************************************************************/
  10. #include "tm_link.hpp"
  11. #include "../Plugins/Openssl/openssl.hpp"
  12. #include "timer.hpp"
  13. /******************************************************************************
  14. * Sending data by packets
  15. ******************************************************************************/
  16. static bool
  17. message_complete (string s) {
  18. int start= 0;
  19. int i, n= N(s);
  20. if (n>0 && s[0] == '!') start= 1;
  21. for (i=start; i<n; i++)
  22. if (s[i] == '\n') break;
  23. if (i == n) return false;
  24. return (n - (i+1)) >= as_int (s (start, i));
  25. }
  26. static string
  27. message_receive (string& s) {
  28. int start= 0;
  29. int i, n= N(s);
  30. if (n>0 && s[0] == '!') start= 1;
  31. for (i=start; i<n; i++)
  32. if (s[i] == '\n') break;
  33. if (i == n) return "";
  34. int l= as_int (s (start, i++));
  35. string r= s (i, i+l);
  36. s= s (i+l, n);
  37. return r;
  38. }
  39. void
  40. tm_link_rep::write_packet (string s, int channel) {
  41. if (secret != "") s= secret_encode (s, secret);
  42. write ((as_string (N (s)) * "\n") * s, channel);
  43. }
  44. bool
  45. tm_link_rep::complete_packet (int channel) {
  46. return message_complete (watch (channel));
  47. }
  48. string
  49. tm_link_rep::read_packet (int channel, int timeout, bool& success) {
  50. success= false;
  51. string& r= watch (channel);
  52. time_t start= texmacs_time ();
  53. while (!message_complete (r)) {
  54. int n= N(r);
  55. if (timeout > 0) listen (timeout);
  56. if (N(r) == n && (texmacs_time () - start >= timeout)) return "";
  57. }
  58. if (channel == LINK_OUT && N(r) > 0 && r[0] == '!') {
  59. secure_server (message_receive (r));
  60. return "";
  61. }
  62. else {
  63. string back= message_receive (r);
  64. if (secret != "") back= secret_decode (back, secret);
  65. success= true;
  66. return back;
  67. }
  68. }
  69. /******************************************************************************
  70. * Data encryption
  71. ******************************************************************************/
  72. void
  73. tm_link_rep::secure_server (string client_public) {
  74. if (secret != "") return;
  75. string k= secret_generate ();
  76. string s= rsa_encode (k, client_public);
  77. write_packet (s, LINK_IN);
  78. secret= k;
  79. }
  80. void
  81. tm_link_rep::secure_client () {
  82. if (secret != "") return;
  83. write ("!", LINK_IN);
  84. write_packet (rsa_my_public_key (), LINK_IN);
  85. bool success;
  86. string r= read_packet (LINK_OUT, 10000, success);
  87. if (!success) { stop (); return; }
  88. secret= rsa_decode (r, rsa_my_private_key ());
  89. }