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.
 
 
 
 
 
 

214 lines
5.4 KiB

  1. /***************************************************************************
  2. * Copyright (C) 2006 by Dominic Rath *
  3. * Dominic.Rath@gmx.de *
  4. * *
  5. * This program is free software; you can redistribute it and/or modify *
  6. * it under the terms of the GNU General Public License as published by *
  7. * the Free Software Foundation; either version 2 of the License, or *
  8. * (at your option) any later version. *
  9. * *
  10. * This program is distributed in the hope that it will be useful, *
  11. * but WITHOUT ANY WARRANTY; without even the implied warranty of *
  12. * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
  13. * GNU General Public License for more details. *
  14. * *
  15. * You should have received a copy of the GNU General Public License *
  16. * along with this program; if not, write to the *
  17. * Free Software Foundation, Inc., *
  18. * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
  19. ***************************************************************************/
  20. #ifdef HAVE_CONFIG_H
  21. #include "config.h"
  22. #endif
  23. #include "pld.h"
  24. #include "log.h"
  25. #include "time_support.h"
  26. /* pld drivers
  27. */
  28. extern pld_driver_t virtex2_pld;
  29. static pld_driver_t *pld_drivers[] =
  30. {
  31. &virtex2_pld,
  32. NULL,
  33. };
  34. static pld_device_t *pld_devices;
  35. static command_t *pld_cmd;
  36. static int handle_pld_devices_command(struct command_context_s *cmd_ctx,
  37. char *cmd, char **args, int argc);
  38. static int handle_pld_device_command(struct command_context_s *cmd_ctx,
  39. char *cmd, char **args, int argc);
  40. static int handle_pld_load_command(struct command_context_s *cmd_ctx,
  41. char *cmd, char **args, int argc);
  42. int pld_init(struct command_context_s *cmd_ctx)
  43. {
  44. if (pld_devices)
  45. {
  46. register_command(cmd_ctx, pld_cmd, "devices", handle_pld_devices_command, COMMAND_EXEC,
  47. "list configured pld devices");
  48. register_command(cmd_ctx, pld_cmd, "load", handle_pld_load_command, COMMAND_EXEC,
  49. "load configuration <file> into programmable logic device");
  50. }
  51. return ERROR_OK;
  52. }
  53. pld_device_t *get_pld_device_by_num(int num)
  54. {
  55. pld_device_t *p;
  56. int i = 0;
  57. for (p = pld_devices; p; p = p->next)
  58. {
  59. if (i++ == num)
  60. {
  61. return p;
  62. }
  63. }
  64. return NULL;
  65. }
  66. /* pld device <driver> [driver_options ...]
  67. */
  68. static int handle_pld_device_command(struct command_context_s *cmd_ctx,
  69. char *cmd, char **args, int argc)
  70. {
  71. int i;
  72. int found = 0;
  73. if (argc < 1)
  74. {
  75. LOG_WARNING("incomplete 'pld device' command");
  76. return ERROR_OK;
  77. }
  78. for (i = 0; pld_drivers[i]; i++)
  79. {
  80. if (strcmp(args[0], pld_drivers[i]->name) == 0)
  81. {
  82. pld_device_t *p, *c;
  83. /* register pld specific commands */
  84. if (pld_drivers[i]->register_commands(cmd_ctx) != ERROR_OK)
  85. {
  86. LOG_ERROR("couldn't register '%s' commands", args[0]);
  87. exit(-1);
  88. }
  89. c = malloc(sizeof(pld_device_t));
  90. c->driver = pld_drivers[i];
  91. c->next = NULL;
  92. if (pld_drivers[i]->pld_device_command(cmd_ctx, cmd, args, argc, c) != ERROR_OK)
  93. {
  94. LOG_ERROR("'%s' driver rejected pld device", args[0]);
  95. free(c);
  96. return ERROR_OK;
  97. }
  98. /* put pld device in linked list */
  99. if (pld_devices)
  100. {
  101. /* find last pld device */
  102. for (p = pld_devices; p && p->next; p = p->next);
  103. if (p)
  104. p->next = c;
  105. }
  106. else
  107. {
  108. pld_devices = c;
  109. }
  110. found = 1;
  111. }
  112. }
  113. /* no matching pld driver found */
  114. if (!found)
  115. {
  116. LOG_ERROR("pld driver '%s' not found", args[0]);
  117. exit(-1);
  118. }
  119. return ERROR_OK;
  120. }
  121. static int handle_pld_devices_command(struct command_context_s *cmd_ctx,
  122. char *cmd, char **args, int argc)
  123. {
  124. pld_device_t *p;
  125. int i = 0;
  126. if (!pld_devices)
  127. {
  128. command_print(cmd_ctx, "no pld devices configured");
  129. return ERROR_OK;
  130. }
  131. for (p = pld_devices; p; p = p->next)
  132. {
  133. command_print(cmd_ctx, "#%i: %s", i++, p->driver->name);
  134. }
  135. return ERROR_OK;
  136. }
  137. static int handle_pld_load_command(struct command_context_s *cmd_ctx,
  138. char *cmd, char **args, int argc)
  139. {
  140. int retval;
  141. struct timeval start, end, duration;
  142. pld_device_t *p;
  143. gettimeofday(&start, NULL);
  144. if (argc < 2)
  145. {
  146. command_print(cmd_ctx, "usage: pld load <device#> <file>");
  147. return ERROR_OK;
  148. }
  149. p = get_pld_device_by_num(strtoul(args[0], NULL, 0));
  150. if (!p)
  151. {
  152. command_print(cmd_ctx, "pld device '#%s' is out of bounds", args[0]);
  153. return ERROR_OK;
  154. }
  155. if ((retval = p->driver->load(p, args[1])) != ERROR_OK)
  156. {
  157. command_print(cmd_ctx, "failed loading file %s to pld device %lu",
  158. args[1], strtoul(args[0], NULL, 0));
  159. switch (retval)
  160. {
  161. }
  162. }
  163. else
  164. {
  165. gettimeofday(&end, NULL);
  166. timeval_subtract(&duration, &end, &start);
  167. command_print(cmd_ctx, "loaded file %s to pld device %lu in %jis %jius",
  168. args[1], strtoul(args[0], NULL, 0),
  169. (intmax_t)duration.tv_sec, (intmax_t)duration.tv_usec);
  170. }
  171. return ERROR_OK;
  172. }
  173. int pld_register_commands(struct command_context_s *cmd_ctx)
  174. {
  175. pld_cmd = register_command(cmd_ctx, NULL, "pld", NULL, COMMAND_ANY, "programmable logic device commands");
  176. register_command(cmd_ctx, pld_cmd, "device", handle_pld_device_command, COMMAND_CONFIG, NULL);
  177. return ERROR_OK;
  178. }