PageRenderTime 64ms CodeModel.GetById 35ms RepoModel.GetById 1ms app.codeStats 0ms

/examples/smc91111_eeprom.c

https://github.com/neuros/u-boot
C | 398 lines | 305 code | 54 blank | 39 comment | 99 complexity | 8f34db066b5b41a420cfa5006e7dab3b MD5 | raw file
Possible License(s): AGPL-1.0
  1. /*
  2. * (C) Copyright 2004
  3. * Robin Getz rgetz@blacfin.uclinux.org
  4. *
  5. * See file CREDITS for list of people who contributed to this
  6. * project.
  7. *
  8. * This program is free software; you can redistribute it and/or
  9. * modify it under the terms of the GNU General Public License as
  10. * published by the Free Software Foundation; either version 2 of
  11. * the License, or (at your option) any later version.
  12. *
  13. * This program is distributed in the hope that it will be useful,
  14. * but WITHOUT ANY WARRANTY; without even the implied warranty of
  15. * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  16. * GNU General Public License for more details.
  17. *
  18. * You should have received a copy of the GNU General Public License
  19. * along with this program; if not, write to the Free Software
  20. * Foundation, Inc., 59 Temple Place, Suite 330, Boston,
  21. * MA 02111-1307 USA
  22. *
  23. * Heavily borrowed from the following peoples GPL'ed software:
  24. * - Wolfgang Denk, DENX Software Engineering, wd@denx.de
  25. * Das U-boot
  26. * - Ladislav Michl ladis@linux-mips.org
  27. * A rejected patch on the U-Boot mailing list
  28. */
  29. #include <common.h>
  30. #include <exports.h>
  31. #include "../drivers/net/smc91111.h"
  32. #ifdef CONFIG_DRIVER_SMC91111
  33. #ifdef pFIO0_DIR
  34. # define pFIO_DIR pFIO0_DIR
  35. # define pFIO_FLAG_S pFIO0_FLAG_S
  36. #endif
  37. #define SMC_BASE_ADDRESS CONFIG_SMC91111_BASE
  38. #define EEPROM 0x1;
  39. #define MAC 0x2;
  40. #define UNKNOWN 0x4;
  41. void dump_reg (void);
  42. void dump_eeprom (void);
  43. int write_eeprom_reg (int, int);
  44. void copy_from_eeprom (void);
  45. void print_MAC (void);
  46. int read_eeprom_reg (int);
  47. void print_macaddr (void);
  48. int smc91111_eeprom (int argc, char *argv[])
  49. {
  50. int c, i, j, done, line, reg, value, start, what;
  51. char input[50];
  52. /* Print the ABI version */
  53. app_startup (argv);
  54. if (XF_VERSION != (int) get_version ()) {
  55. printf ("Expects ABI version %d\n", XF_VERSION);
  56. printf ("Actual U-Boot ABI version %d\n",
  57. (int) get_version ());
  58. printf ("Can't run\n\n");
  59. return (0);
  60. }
  61. *pFIO_DIR = 0x01;
  62. *pFIO_FLAG_S = 0x01;
  63. SSYNC();
  64. if ((SMC_inw (BANK_SELECT) & 0xFF00) != 0x3300) {
  65. printf ("Can't find SMSC91111\n");
  66. return (0);
  67. }
  68. done = 0;
  69. what = UNKNOWN;
  70. printf ("\n");
  71. while (!done) {
  72. /* print the prompt */
  73. printf ("SMC91111> ");
  74. line = 0;
  75. i = 0;
  76. start = 1;
  77. while (!line) {
  78. /* Wait for a keystroke */
  79. while (!tstc ());
  80. c = getc ();
  81. /* Make Uppercase */
  82. if (c >= 'Z')
  83. c -= ('a' - 'A');
  84. /* printf(" |%02x| ",c); */
  85. switch (c) {
  86. case '\r': /* Enter */
  87. case '\n':
  88. input[i] = 0;
  89. puts ("\r\n");
  90. line = 1;
  91. break;
  92. case '\0': /* nul */
  93. continue;
  94. case 0x03: /* ^C - break */
  95. input[0] = 0;
  96. i = 0;
  97. line = 1;
  98. done = 1;
  99. break;
  100. case 0x5F:
  101. case 0x08: /* ^H - backspace */
  102. case 0x7F: /* DEL - backspace */
  103. if (i > 0) {
  104. puts ("\b \b");
  105. i--;
  106. }
  107. break;
  108. default:
  109. if (start) {
  110. if ((c == 'W') || (c == 'D')
  111. || (c == 'M') || (c == 'C')
  112. || (c == 'P')) {
  113. putc (c);
  114. input[i] = c;
  115. if (i <= 45)
  116. i++;
  117. start = 0;
  118. }
  119. } else {
  120. if ((c >= '0' && c <= '9')
  121. || (c >= 'A' && c <= 'F')
  122. || (c == 'E') || (c == 'M')
  123. || (c == ' ')) {
  124. putc (c);
  125. input[i] = c;
  126. if (i <= 45)
  127. i++;
  128. break;
  129. }
  130. }
  131. break;
  132. }
  133. }
  134. for (; i < 49; i++)
  135. input[i] = 0;
  136. switch (input[0]) {
  137. case ('W'):
  138. /* Line should be w reg value */
  139. i = 0;
  140. reg = 0;
  141. value = 0;
  142. /* Skip to the next space or end) */
  143. while ((input[i] != ' ') && (input[i] != 0))
  144. i++;
  145. if (input[i] != 0)
  146. i++;
  147. /* Are we writing to EEPROM or MAC */
  148. switch (input[i]) {
  149. case ('E'):
  150. what = EEPROM;
  151. break;
  152. case ('M'):
  153. what = MAC;
  154. break;
  155. default:
  156. what = UNKNOWN;
  157. break;
  158. }
  159. /* skip to the next space or end */
  160. while ((input[i] != ' ') && (input[i] != 0))
  161. i++;
  162. if (input[i] != 0)
  163. i++;
  164. /* Find register to write into */
  165. j = 0;
  166. while ((input[i] != ' ') && (input[i] != 0)) {
  167. j = input[i] - 0x30;
  168. if (j >= 0xA) {
  169. j -= 0x07;
  170. }
  171. reg = (reg * 0x10) + j;
  172. i++;
  173. }
  174. while ((input[i] != ' ') && (input[i] != 0))
  175. i++;
  176. if (input[i] != 0)
  177. i++;
  178. else
  179. what = UNKNOWN;
  180. /* Get the value to write */
  181. j = 0;
  182. while ((input[i] != ' ') && (input[i] != 0)) {
  183. j = input[i] - 0x30;
  184. if (j >= 0xA) {
  185. j -= 0x07;
  186. }
  187. value = (value * 0x10) + j;
  188. i++;
  189. }
  190. switch (what) {
  191. case 1:
  192. printf ("Writing EEPROM register %02x with %04x\n", reg, value);
  193. write_eeprom_reg (value, reg);
  194. break;
  195. case 2:
  196. printf ("Writing MAC register bank %i, reg %02x with %04x\n", reg >> 4, reg & 0xE, value);
  197. SMC_SELECT_BANK (reg >> 4);
  198. SMC_outw (value, reg & 0xE);
  199. break;
  200. default:
  201. printf ("Wrong\n");
  202. break;
  203. }
  204. break;
  205. case ('D'):
  206. dump_eeprom ();
  207. break;
  208. case ('M'):
  209. dump_reg ();
  210. break;
  211. case ('C'):
  212. copy_from_eeprom ();
  213. break;
  214. case ('P'):
  215. print_macaddr ();
  216. break;
  217. default:
  218. break;
  219. }
  220. }
  221. return (0);
  222. }
  223. void copy_from_eeprom (void)
  224. {
  225. int i;
  226. SMC_SELECT_BANK (1);
  227. SMC_outw ((SMC_inw (CTL_REG) & !CTL_EEPROM_SELECT) | CTL_RELOAD,
  228. CTL_REG);
  229. i = 100;
  230. while ((SMC_inw (CTL_REG) & CTL_RELOAD) && --i)
  231. udelay (100);
  232. if (i == 0) {
  233. printf ("Timeout Refreshing EEPROM registers\n");
  234. } else {
  235. printf ("EEPROM contents copied to MAC\n");
  236. }
  237. }
  238. void print_macaddr (void)
  239. {
  240. int i, j, k, mac[6];
  241. printf ("Current MAC Address in SMSC91111 ");
  242. SMC_SELECT_BANK (1);
  243. for (i = 0; i < 5; i++) {
  244. printf ("%02x:", SMC_inb (ADDR0_REG + i));
  245. }
  246. printf ("%02x\n", SMC_inb (ADDR0_REG + 5));
  247. i = 0;
  248. for (j = 0x20; j < 0x23; j++) {
  249. k = read_eeprom_reg (j);
  250. mac[i] = k & 0xFF;
  251. i++;
  252. mac[i] = k >> 8;
  253. i++;
  254. }
  255. printf ("Current MAC Address in EEPROM ");
  256. for (i = 0; i < 5; i++)
  257. printf ("%02x:", mac[i]);
  258. printf ("%02x\n", mac[5]);
  259. }
  260. void dump_eeprom (void)
  261. {
  262. int j, k;
  263. printf ("IOS2-0 ");
  264. for (j = 0; j < 8; j++) {
  265. printf ("%03x ", j);
  266. }
  267. printf ("\n");
  268. for (k = 0; k < 4; k++) {
  269. if (k == 0)
  270. printf ("CONFIG ");
  271. if (k == 1)
  272. printf ("BASE ");
  273. if ((k == 2) || (k == 3))
  274. printf (" ");
  275. for (j = 0; j < 0x20; j += 4) {
  276. printf ("%02x:%04x ", j + k, read_eeprom_reg (j + k));
  277. }
  278. printf ("\n");
  279. }
  280. for (j = 0x20; j < 0x40; j++) {
  281. if ((j & 0x07) == 0)
  282. printf ("\n");
  283. printf ("%02x:%04x ", j, read_eeprom_reg (j));
  284. }
  285. printf ("\n");
  286. }
  287. int read_eeprom_reg (int reg)
  288. {
  289. int timeout;
  290. SMC_SELECT_BANK (2);
  291. SMC_outw (reg, PTR_REG);
  292. SMC_SELECT_BANK (1);
  293. SMC_outw (SMC_inw (CTL_REG) | CTL_EEPROM_SELECT | CTL_RELOAD,
  294. CTL_REG);
  295. timeout = 100;
  296. while ((SMC_inw (CTL_REG) & CTL_RELOAD) && --timeout)
  297. udelay (100);
  298. if (timeout == 0) {
  299. printf ("Timeout Reading EEPROM register %02x\n", reg);
  300. return 0;
  301. }
  302. return SMC_inw (GP_REG);
  303. }
  304. int write_eeprom_reg (int value, int reg)
  305. {
  306. int timeout;
  307. SMC_SELECT_BANK (2);
  308. SMC_outw (reg, PTR_REG);
  309. SMC_SELECT_BANK (1);
  310. SMC_outw (value, GP_REG);
  311. SMC_outw (SMC_inw (CTL_REG) | CTL_EEPROM_SELECT | CTL_STORE, CTL_REG);
  312. timeout = 100;
  313. while ((SMC_inw (CTL_REG) & CTL_STORE) && --timeout)
  314. udelay (100);
  315. if (timeout == 0) {
  316. printf ("Timeout Writing EEPROM register %02x\n", reg);
  317. return 0;
  318. }
  319. return 1;
  320. }
  321. void dump_reg (void)
  322. {
  323. int i, j;
  324. printf (" ");
  325. for (j = 0; j < 4; j++) {
  326. printf ("Bank%i ", j);
  327. }
  328. printf ("\n");
  329. for (i = 0; i < 0xF; i += 2) {
  330. printf ("%02x ", i);
  331. for (j = 0; j < 4; j++) {
  332. SMC_SELECT_BANK (j);
  333. printf ("%04x ", SMC_inw (i));
  334. }
  335. printf ("\n");
  336. }
  337. }
  338. #else
  339. int smc91111_eeprom (int argc, char *argv[])
  340. {
  341. printf("Not supported for this board\n");
  342. return 1;
  343. }
  344. #endif