lua_in_finsh.c 4.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184
  1. /**
  2. * run lua interpreter from finsh
  3. */
  4. #include "rtthread.h"
  5. #include "finsh.h"
  6. #include "shell.h"
  7. struct
  8. {
  9. struct rt_semaphore sem;
  10. rt_device_t device;
  11. } dev4lua;
  12. extern int lua_main(int argc, char **argv);
  13. rt_err_t lua_rx_ind(rt_device_t dev, rt_size_t size)
  14. {
  15. rt_sem_release(&dev4lua.sem);
  16. return RT_EOK;
  17. }
  18. void finsh_lua(int argc, char **argv)
  19. {
  20. rt_err_t (*rx_indicate)(rt_device_t dev, rt_size_t size);
  21. rt_sem_init(&(dev4lua.sem), "luasem", 0, 0);
  22. /* save old rx_indicate */
  23. rx_indicate = dev4lua.device->rx_indicate;
  24. /* set new rx_indicate */
  25. rt_device_set_rx_indicate(dev4lua.device, lua_rx_ind);
  26. {
  27. /* run lua interpreter */
  28. lua_main(argc, argv);
  29. }
  30. /* recover old rx_indicate */
  31. rt_device_set_rx_indicate(dev4lua.device, rx_indicate);
  32. }
  33. static void lua(void *parameters)
  34. {
  35. const char* device_name = finsh_get_device();
  36. rt_device_t device = rt_device_find(device_name);
  37. if (device == RT_NULL)
  38. {
  39. rt_kprintf("%s not find\n", device_name);
  40. return;
  41. }
  42. dev4lua.device = device;
  43. char *argv[] = {"lua", parameters, NULL};
  44. #if 0
  45. /* Run lua interpreter in separate thread */
  46. lua_thread = rt_thread_create("lua",
  47. finsh_lua,
  48. 0,
  49. 2048,
  50. rt_thread_self()->current_priority + 1,
  51. 20);
  52. if (lua_thread != RT_NULL)
  53. {
  54. rt_thread_startup(lua_thread);
  55. }
  56. #else
  57. /* Directly run lua interpreter in finsh */
  58. finsh_lua(2, argv);
  59. #endif
  60. }
  61. FINSH_FUNCTION_EXPORT(lua, lua interpreter);
  62. static void lua_msh(int argc, char **argv)
  63. {
  64. const char* device_name = finsh_get_device();
  65. rt_device_t device = rt_device_find(device_name);
  66. if (device == RT_NULL)
  67. {
  68. rt_kprintf("%s not find\n", device_name);
  69. return;
  70. }
  71. dev4lua.device = device;
  72. /*prepare parameters*/
  73. int i;
  74. char **arg = rt_malloc((argc+1)*sizeof(char*));
  75. for (i=0; i<argc; i++){
  76. arg[i] = argv[i];
  77. }
  78. arg[argc] = NULL;
  79. finsh_lua(argc, arg);
  80. rt_free(arg);
  81. return;
  82. }
  83. MSH_CMD_EXPORT(lua_msh, lua in msh);
  84. int readline4lua(const char *prompt, char *buffer, int buffer_size)
  85. {
  86. char ch;
  87. int line_position;
  88. start:
  89. /* show prompt */
  90. rt_kprintf(prompt);
  91. line_position = 0;
  92. memset(buffer, 0, buffer_size);
  93. while (1)
  94. {
  95. if (rt_sem_take(&dev4lua.sem, RT_WAITING_FOREVER) != RT_EOK)
  96. {
  97. return 0;
  98. }
  99. while (rt_device_read(dev4lua.device, 0, &ch, 1) == 1)
  100. {
  101. /* handle CR key */
  102. if (ch == '\r')
  103. {
  104. char next;
  105. if (rt_device_read(dev4lua.device, 0, &next, 1) == 1)
  106. ch = next;
  107. }
  108. /* backspace key */
  109. else if (ch == 0x7f || ch == 0x08)
  110. {
  111. if (line_position > 0)
  112. {
  113. rt_kprintf("%c %c", ch, ch);
  114. line_position--;
  115. }
  116. buffer[line_position] = 0;
  117. continue;
  118. }
  119. /* EOF(ctrl+d) */
  120. else if (ch == 0x04)
  121. {
  122. if (line_position == 0)
  123. /* No input which makes lua interpreter close */
  124. return 0;
  125. else
  126. continue;
  127. }
  128. /* end of line */
  129. if (ch == '\r' || ch == '\n')
  130. {
  131. buffer[line_position] = 0;
  132. rt_kprintf("\n");
  133. if (line_position == 0)
  134. {
  135. /* Get a empty line, then go to get a new line */
  136. goto start;
  137. }
  138. else
  139. {
  140. return line_position;
  141. }
  142. }
  143. /* other control character or not an acsii character */
  144. if (ch < 0x20 || ch >= 0x80)
  145. {
  146. continue;
  147. }
  148. /* echo */
  149. rt_kprintf("%c", ch);
  150. buffer[line_position] = ch;
  151. ch = 0;
  152. line_position++;
  153. /* it's a large line, discard it */
  154. if (line_position >= buffer_size)
  155. line_position = 0;
  156. }
  157. }
  158. }