ES-2024 reverter
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.

121 lines
2.5KB

  1. #include <stdio.h>
  2. #include <stdlib.h>
  3. #include <unistd.h>
  4. #include <string.h>
  5. #include <termios.h>
  6. #include "context.h"
  7. #include "linebuffer.h"
  8. #include "logging.h"
  9. #include "xmodem.h"
  10. /* states */
  11. enum {
  12. STATE_NONE = 0,
  13. STATE_DEBUG_ASK, /* waiting for "Press any key.." */
  14. STATE_DEBUG, /* debug mode entered */
  15. STATE_SWITCH_BAUDRATE, /* switching baudrate */
  16. STATE_XMODEM, /* xmodem active */
  17. STATE_XMODEM_COMPLETE, /* xmodem complete */
  18. STATE_BOOT, /* booting firmware */
  19. };
  20. /* messages */
  21. char *rx_msg[] = {
  22. "Press any key to enter debug mode within 3 seconds.",
  23. "Enter Debug Mode",
  24. "Now, console speed will be changed to 115200 bps",
  25. "OK",
  26. "Console speed will be changed to 9600 bps",
  27. NULL
  28. };
  29. /* message IDs */
  30. enum {
  31. MSG_DEBUG_ASK = 0,
  32. MSG_DEBUG,
  33. MSG_BAUD_HIGH,
  34. MSG_XMODEM_OK,
  35. MSG_BAUD_LOW,
  36. };
  37. int statemachine_read(int fd, void *privdata)
  38. {
  39. struct context *ctx = (struct context *)privdata;
  40. if (ctx->state == STATE_XMODEM) {
  41. if (xmodem_read(fd, privdata) < 0)
  42. ctx->state = STATE_XMODEM_COMPLETE;
  43. return 0;
  44. }
  45. if (linebuffer_read(ctx->lbuf, fd) < 0)
  46. return -1;
  47. char *line;
  48. while ((line = linebuffer_get(ctx->lbuf)) != NULL) {
  49. log_print(LOG_DEBUG, "%s: '%s'", ctx->devname, line);
  50. int msg = 0;
  51. while (rx_msg[msg] != NULL) {
  52. if (strcmp(line, rx_msg[msg]) == 0)
  53. break;
  54. msg++;
  55. }
  56. /* wait for "Press any key" */
  57. if (msg == MSG_DEBUG_ASK) {
  58. ctx->state = STATE_DEBUG_ASK;
  59. write(fd, "\r\n", 2);
  60. /* debug mode entered */
  61. } else if (msg == MSG_DEBUG) {
  62. /* if device supports it, switch to high baudrate */
  63. if ((ctx->flags & FLAG_SPEEDUP) && ctx->dev_setbaudrate != NULL) {
  64. ctx->state = STATE_SWITCH_BAUDRATE;
  65. write(fd, "ATBA5\r\n", 7);
  66. } else {
  67. ctx->state = STATE_XMODEM;
  68. if (ctx->flags & FLAG_CONFIG)
  69. write(fd, "ATLC\r\n", 6);
  70. else if (ctx->flags & FLAG_FIRMWARE)
  71. write(fd, "ATUR\r\n", 6);
  72. }
  73. /* follow device to high baudrate */
  74. } else if (msg == MSG_BAUD_HIGH) {
  75. ctx->dev_setbaudrate(ctx, B115200);
  76. linebuffer_clear(ctx->lbuf);
  77. ctx->state = STATE_XMODEM;
  78. if (ctx->flags & FLAG_CONFIG)
  79. write(fd, "ATLC\r\n", 6);
  80. else if (ctx->flags & FLAG_FIRMWARE)
  81. write(fd, "ATUR\r\n", 6);
  82. /* transfer was success */
  83. } else if (msg == MSG_XMODEM_OK && ctx->state == STATE_XMODEM_COMPLETE) {
  84. ctx->state = STATE_BOOT;
  85. write(fd, "ATGR\r\n", 6);
  86. /* follow device to low baudrate */
  87. } else if (msg == MSG_BAUD_LOW) {
  88. ctx->dev_setbaudrate(ctx, B9600);
  89. linebuffer_clear(ctx->lbuf);
  90. }
  91. free(line);
  92. };
  93. return 0;
  94. }