nmi.c 1.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384
  1. /*
  2. * SDK7786 FPGA NMI Support.
  3. *
  4. * Copyright (C) 2010 Paul Mundt
  5. *
  6. * This file is subject to the terms and conditions of the GNU General Public
  7. * License. See the file "COPYING" in the main directory of this archive
  8. * for more details.
  9. */
  10. #include <linux/init.h>
  11. #include <linux/kernel.h>
  12. #include <linux/string.h>
  13. #include <mach/fpga.h>
  14. enum {
  15. NMI_MODE_MANUAL,
  16. NMI_MODE_AUX,
  17. NMI_MODE_MASKED,
  18. NMI_MODE_ANY,
  19. NMI_MODE_UNKNOWN,
  20. };
  21. /*
  22. * Default to the manual NMI switch.
  23. */
  24. static unsigned int __initdata nmi_mode = NMI_MODE_ANY;
  25. static int __init nmi_mode_setup(char *str)
  26. {
  27. if (!str)
  28. return 0;
  29. if (strcmp(str, "manual") == 0)
  30. nmi_mode = NMI_MODE_MANUAL;
  31. else if (strcmp(str, "aux") == 0)
  32. nmi_mode = NMI_MODE_AUX;
  33. else if (strcmp(str, "masked") == 0)
  34. nmi_mode = NMI_MODE_MASKED;
  35. else if (strcmp(str, "any") == 0)
  36. nmi_mode = NMI_MODE_ANY;
  37. else {
  38. nmi_mode = NMI_MODE_UNKNOWN;
  39. pr_warning("Unknown NMI mode %s\n", str);
  40. }
  41. printk("Set NMI mode to %d\n", nmi_mode);
  42. return 0;
  43. }
  44. early_param("nmi_mode", nmi_mode_setup);
  45. void __init sdk7786_nmi_init(void)
  46. {
  47. unsigned int source, mask, tmp;
  48. switch (nmi_mode) {
  49. case NMI_MODE_MANUAL:
  50. source = NMISR_MAN_NMI;
  51. mask = NMIMR_MAN_NMIM;
  52. break;
  53. case NMI_MODE_AUX:
  54. source = NMISR_AUX_NMI;
  55. mask = NMIMR_AUX_NMIM;
  56. break;
  57. case NMI_MODE_ANY:
  58. source = NMISR_MAN_NMI | NMISR_AUX_NMI;
  59. mask = NMIMR_MAN_NMIM | NMIMR_AUX_NMIM;
  60. break;
  61. case NMI_MODE_MASKED:
  62. case NMI_MODE_UNKNOWN:
  63. default:
  64. source = mask = 0;
  65. break;
  66. }
  67. /* Set the NMI source */
  68. tmp = fpga_read_reg(NMISR);
  69. tmp &= ~NMISR_MASK;
  70. tmp |= source;
  71. fpga_write_reg(tmp, NMISR);
  72. /* And the IRQ masking */
  73. fpga_write_reg(NMIMR_MASK ^ mask, NMIMR);
  74. }